diff --git a/dev/build.xml b/dev/build.xml
index 014a432..9652c46 100755
--- a/dev/build.xml
+++ b/dev/build.xml
@@ -221,6 +221,19 @@
     <antcall target="-filter.props" />
   </target>
 
+  <target name="generate.remotemessageproto.java">
+    <!-- Generate the java code -->
+    <exec executable="protoc" failonerror="true">
+        <arg value="--java_out=core/src"/>
+        <arg value="./core/src/com/google/gwt/dev/shell/remoteui/remotemessage.proto"/>
+    </exec>
+      
+    <!-- Rebase the java code to match the rebased protobuf library -->
+    <replace file="./core/src/com/google/gwt/dev/shell/remoteui/RemoteMessageProto.java">
+        <replacefilter token="com.google.protobuf" value="com.google.gwt.dev.protobuf"/>
+    </replace>
+  </target>
+      
   <target name="checkstyle" description="Static analysis of source">
     <gwt.checkstyle>
       <fileset dir="core/src">
diff --git a/dev/core/src/com/google/gwt/dev/DevModeBase.java b/dev/core/src/com/google/gwt/dev/DevModeBase.java
index ebe9592..6c0ddeb 100644
--- a/dev/core/src/com/google/gwt/dev/DevModeBase.java
+++ b/dev/core/src/com/google/gwt/dev/DevModeBase.java
@@ -52,7 +52,9 @@
 import com.google.gwt.util.tools.ArgHandlerString;
 
 import java.io.File;
+import java.io.IOException;
 import java.net.MalformedURLException;
+import java.net.ServerSocket;
 import java.net.URL;
 import java.util.ArrayList;
 import java.util.Collections;
@@ -275,7 +277,7 @@
     @Override
     public boolean setString(String value) {
       if (value.equals("auto")) {
-        options.setPort(0);
+        options.setPort(getFreeSocketPort());
       } else {
         try {
           options.setPort(Integer.parseInt(value));
@@ -322,7 +324,7 @@
     @Override
     public boolean setString(String value) {
       if (value.equals("auto")) {
-        options.setPortHosted(0);
+        options.setPortHosted(getFreeSocketPort());
       } else {
         try {
           options.setPortHosted(Integer.parseInt(value));
@@ -337,9 +339,9 @@
 
   protected static class ArgHandlerRemoteUI extends ArgHandlerString {
 
-    private final OptionUI options;
+    private final HostedModeBaseOptions options;
 
-    public ArgHandlerRemoteUI(OptionUI options) {
+    public ArgHandlerRemoteUI(HostedModeBaseOptions options) {
       this.options = options;
     }
 
@@ -355,7 +357,7 @@
 
     @Override
     public String[] getTagArgs() {
-      return new String[] {"port-number | host-string:port-number"};
+      return new String[] {"port-number:client-id-string | host-string:port-number:client-id-string"};
     }
 
     @Override
@@ -363,17 +365,24 @@
       String[] split = str.split(":");
       String hostStr = "localhost";
       String portStr = null;
+      String clientId;
 
-      if (split.length > 1) {
+      if (split.length == 3) {
         hostStr = split[0];
         portStr = split[1];
-      } else {
+        clientId = split[2];
+      } else if (split.length == 2) {
         portStr = split[0];
+        clientId = split[1];
+      } else {
+        return false;
       }
 
+      options.setRemoteUIHost(hostStr);
+      options.setClientId(clientId);
+
       try {
-        RemoteUI remoteUI = new RemoteUI(hostStr, Integer.parseInt(portStr));
-        options.setUI(remoteUI);
+        options.setRemoteUIHostPort(Integer.parseInt(portStr));
       } catch (NumberFormatException nfe) {
         System.err.println("A port must be an integer");
         return false;
@@ -410,7 +419,7 @@
 
   protected interface HostedModeBaseOptions extends JJSOptions, OptionLogDir,
       OptionLogLevel, OptionGenDir, OptionNoServer, OptionPort,
-      OptionPortHosted, OptionStartupURLs, OptionUI {
+      OptionPortHosted, OptionStartupURLs, OptionRemoteUI {
 
     /**
      * The base shell work directory.
@@ -424,15 +433,18 @@
   /**
    * Concrete class to implement all hosted mode base options.
    */
+  @SuppressWarnings("serial")
   protected static class HostedModeBaseOptionsImpl extends
       PrecompileOptionsImpl implements HostedModeBaseOptions {
 
-    private DevModeUI ui;
     private boolean isNoServer;
     private File logDir;
     private int port;
     private int portHosted;
     private final List<String> startupURLs = new ArrayList<String>();
+    private String remoteUIClientId;
+    private String remoteUIHost;
+    private int remoteUIHostPort;
 
     public void addStartupURL(String url) {
       startupURLs.add(url);
@@ -442,6 +454,10 @@
       return logDir != null;
     }
 
+    public String getClientId() {
+      return remoteUIClientId;
+    }
+
     public File getLogDir() {
       return logDir;
     }
@@ -461,6 +477,14 @@
       return portHosted;
     }
 
+    public String getRemoteUIHost() {
+      return remoteUIHost;
+    }
+
+    public int getRemoteUIHostPort() {
+      return remoteUIHostPort;
+    }
+
     public File getShellBaseWorkDir(ModuleDef moduleDef) {
       return new File(new File(getWorkDir(), moduleDef.getName()), "shell");
     }
@@ -469,14 +493,14 @@
       return Collections.unmodifiableList(startupURLs);
     }
 
-    public DevModeUI getUI() {
-      return ui;
-    }
-
     public boolean isNoServer() {
       return isNoServer;
     }
 
+    public void setClientId(String clientId) {
+      this.remoteUIClientId = clientId;
+    }
+
     public void setLogFile(String filename) {
       logDir = new File(filename);
     }
@@ -493,8 +517,16 @@
       portHosted = port;
     }
 
-    public void setUI(DevModeUI ui) {
-      this.ui = ui;
+    public void setRemoteUIHost(String remoteUIHost) {
+      this.remoteUIHost = remoteUIHost;
+    }
+
+    public void setRemoteUIHostPort(int remoteUIHostPort) {
+      this.remoteUIHostPort = remoteUIHostPort;
+    }
+
+    public boolean useRemoteUI() {
+      return remoteUIHost != null;
     }
   }
 
@@ -539,6 +571,25 @@
   }
 
   /**
+   * Controls the UI that should be used to display the dev mode server's data.
+   */
+  protected interface OptionRemoteUI {
+    String getClientId();
+
+    String getRemoteUIHost();
+
+    int getRemoteUIHostPort();
+
+    void setClientId(String clientId);
+
+    void setRemoteUIHost(String remoteUIHost);
+
+    void setRemoteUIHostPort(int remoteUIHostPort);
+
+    boolean useRemoteUI();
+  }
+
+  /**
    * Controls the startup URLs.
    */
   protected interface OptionStartupURLs {
@@ -547,15 +598,6 @@
     List<String> getStartupURLs();
   }
 
-  /**
-   * Controls the UI that should be used to display the dev mode server's data.
-   */
-  protected interface OptionUI {
-    DevModeUI getUI();
-
-    void setUI(DevModeUI ui);
-  }
-
   abstract static class ArgProcessor extends ArgProcessorBase {
     public ArgProcessor(HostedModeBaseOptions options, boolean forceServer) {
       if (!forceServer) {
@@ -602,6 +644,27 @@
   }
 
   /**
+   * Returns a free port. The returned port should not be returned again unless
+   * the ephemeral port range is exhausted.
+   */
+  protected static int getFreeSocketPort() {
+    ServerSocket socket = null;
+    try {
+      socket = new ServerSocket(0);
+      return socket.getLocalPort();
+    } catch (IOException e) {
+    } finally {
+      if (socket != null) {
+        try {
+          socket.close();
+        } catch (IOException e) {
+        }
+      }
+    }
+    return -1;
+  }
+
+  /**
    * Produce a random string that has low probability of collisions.
    * 
    * <p>
@@ -878,7 +941,7 @@
       String path = parsedUrl.getPath();
       String query = parsedUrl.getQuery();
       String hash = parsedUrl.getRef();
-      String hostedParam = "gwt.hosted=" + listener.getEndpointIdentifier();
+      String hostedParam = BrowserListener.getDevModeURLParams(listener.getEndpointIdentifier());
       if (query == null) {
         query = hostedParam;
       } else {
@@ -941,16 +1004,7 @@
     }
 
     // See if there was a UI specified by command-line args
-    ui = options.getUI();
-
-    // If no UI was specified by command-line args, then create one.
-    if (ui == null) {
-      if (headlessMode) {
-        ui = new HeadlessUI(options);
-      } else {
-        ui = new SwingUI(options);
-      }
-    }
+    ui = createUI();
 
     started = true;
 
@@ -970,4 +1024,18 @@
 
     return true;
   }
+
+  private DevModeUI createUI() {
+    if (headlessMode) {
+      return new HeadlessUI(options);
+    } else {
+      if (options.useRemoteUI()) {
+        return new RemoteUI(options.getRemoteUIHost(),
+            options.getRemoteUIHostPort(), options.getClientId(),
+            options.getPort(), options.getPortHosted());
+      }
+    }
+
+    return new SwingUI(options);
+  }
 }
diff --git a/dev/core/src/com/google/gwt/dev/shell/BrowserListener.java b/dev/core/src/com/google/gwt/dev/shell/BrowserListener.java
index 9b65ebe..2dd16be 100644
--- a/dev/core/src/com/google/gwt/dev/shell/BrowserListener.java
+++ b/dev/core/src/com/google/gwt/dev/shell/BrowserListener.java
@@ -32,12 +32,25 @@
  */
 public class BrowserListener {
 
+  public static String computeEndpointIdentifier(int browserChannelPort) {
+    try {
+      return InetAddress.getLocalHost().getHostAddress() + ":"
+          + browserChannelPort;
+    } catch (UnknownHostException e) {
+      throw new RuntimeException("Unable to determine my ip", e);
+    }
+  }
+
+  public static String getDevModeURLParams(String endpointIdentifier) {
+    return "gwt.hosted=" + endpointIdentifier;
+  }
+
   private ServerSocket listenSocket;
 
   private Thread listenThread;
-
+  
   private boolean ignoreRemoteDeath = false;
-
+  
   /**
    * Listens for new connections from browsers.
    */
@@ -102,12 +115,7 @@
       // If we failed to initialize our socket, just bail here.
       throw new UnableToCompleteException();
     }
-    try {
-      return InetAddress.getLocalHost().getHostAddress() + ":"
-          + listenSocket.getLocalPort();
-    } catch (UnknownHostException e) {
-      throw new RuntimeException("Unable to determine my ip", e);
-    }
+    return computeEndpointIdentifier(listenSocket.getLocalPort());
   }
 
   /**
diff --git a/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteMessageProto.java b/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteMessageProto.java
index e9e115e..8f00e41 100644
--- a/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteMessageProto.java
+++ b/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteMessageProto.java
@@ -1,1870 +1,1920 @@
-// Generated by the protocol buffer compiler. DO NOT EDIT!
-
-// This file was hand-edited to rebase the com.google.protobuf package
-// to com.google.gwt.dev.protobuf
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
 
 package com.google.gwt.dev.shell.remoteui;
 
 public final class RemoteMessageProto {
+  private RemoteMessageProto() {}
+  public static void registerAllExtensions(
+      com.google.gwt.dev.protobuf.ExtensionRegistry registry) {
+  }
   public static final class Message extends
       com.google.gwt.dev.protobuf.GeneratedMessage {
-    public static final class Builder extends
-        com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-      private static Builder create() {
-        Builder builder = new Builder();
-        builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message();
-        return builder;
-      }
-
-      private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message result;
-
-      // Construct using
-      // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.newBuilder()
-      private Builder() {
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message build() {
-        if (result != null && !isInitialized()) {
-          throw newUninitializedMessageException(result);
-        }
-        return buildPartial();
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message buildPartial() {
-        if (result == null) {
-          throw new IllegalStateException(
-              "build() has already been called on this Builder.");
-        }
-        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message returnMe = result;
-        result = null;
-        return returnMe;
-      }
-
-      public Builder clear() {
-        if (result == null) {
-          throw new IllegalStateException("Cannot call clear() after build().");
-        }
-        result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message();
-        return this;
-      }
-
-      public Builder clearMessageType() {
-        result.hasMessageType = false;
-        result.messageType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType.REQUEST;
-        return this;
-      }
-
-      public Builder clearRequest() {
-        result.hasRequest = false;
-        result.request_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance();
-        return this;
-      }
-
-      public Builder clearResponse() {
-        result.hasResponse = false;
-        result.response_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance();
-        return this;
-      }
-
-      public Builder clone() {
-        return create().mergeFrom(result);
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message getDefaultInstanceForType() {
-        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDefaultInstance();
-      }
-
-      public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDescriptor();
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType getMessageType() {
-        return result.getMessageType();
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request getRequest() {
-        return result.getRequest();
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response getResponse() {
-        return result.getResponse();
-      }
-
-      // required .com.google.gwt.dev.shell.remoteui.Message.MessageType
-      // messageType = 1;
-      public boolean hasMessageType() {
-        return result.hasMessageType();
-      }
-
-      // optional .com.google.gwt.dev.shell.remoteui.Message.Request request =
-      // 2;
-      public boolean hasRequest() {
-        return result.hasRequest();
-      }
-
-      // optional .com.google.gwt.dev.shell.remoteui.Message.Response response =
-      // 3;
-      public boolean hasResponse() {
-        return result.hasResponse();
-      }
-
-      public boolean isInitialized() {
-        return result.isInitialized();
-      }
-
-      public Builder mergeFrom(
-          com.google.gwt.dev.protobuf.CodedInputStream input,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws java.io.IOException {
-        com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-        while (true) {
-          int tag = input.readTag();
-          switch (tag) {
-            case 0:
-              this.setUnknownFields(unknownFields.build());
-              return this;
-            default: {
-              if (!parseUnknownField(input, unknownFields, extensionRegistry,
-                  tag)) {
-                this.setUnknownFields(unknownFields.build());
-                return this;
-              }
-              break;
-            }
-            case 8: {
-              int rawValue = input.readEnum();
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType.valueOf(rawValue);
-              if (value == null) {
-                unknownFields.mergeVarintField(1, rawValue);
-              } else {
-                setMessageType(value);
-              }
-              break;
-            }
-            case 18: {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.newBuilder();
-              if (hasRequest()) {
-                subBuilder.mergeFrom(getRequest());
-              }
-              input.readMessage(subBuilder, extensionRegistry);
-              setRequest(subBuilder.buildPartial());
-              break;
-            }
-            case 26: {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.newBuilder();
-              if (hasResponse()) {
-                subBuilder.mergeFrom(getResponse());
-              }
-              input.readMessage(subBuilder, extensionRegistry);
-              setResponse(subBuilder.buildPartial());
-              break;
-            }
-          }
-        }
-      }
-
-      public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-        if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message) {
-          return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message) other);
-        } else {
-          super.mergeFrom(other);
-          return this;
-        }
-      }
-
-      public Builder mergeFrom(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message other) {
-        if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDefaultInstance())
-          return this;
-        if (other.hasMessageType()) {
-          setMessageType(other.getMessageType());
-        }
-        if (other.hasRequest()) {
-          mergeRequest(other.getRequest());
-        }
-        if (other.hasResponse()) {
-          mergeResponse(other.getResponse());
-        }
-        this.mergeUnknownFields(other.getUnknownFields());
-        return this;
-      }
-
-      public Builder mergeRequest(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request value) {
-        if (result.hasRequest()
-            && result.request_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance()) {
-          result.request_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.newBuilder(
-              result.request_).mergeFrom(value).buildPartial();
-        } else {
-          result.request_ = value;
-        }
-        result.hasRequest = true;
-        return this;
-      }
-
-      public Builder mergeResponse(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response value) {
-        if (result.hasResponse()
-            && result.response_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance()) {
-          result.response_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.newBuilder(
-              result.response_).mergeFrom(value).buildPartial();
-        } else {
-          result.response_ = value;
-        }
-        result.hasResponse = true;
-        return this;
-      }
-
-      public Builder setMessageType(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType value) {
-        if (value == null) {
-          throw new NullPointerException();
-        }
-        result.hasMessageType = true;
-        result.messageType_ = value;
-        return this;
-      }
-
-      public Builder setRequest(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request value) {
-        if (value == null) {
-          throw new NullPointerException();
-        }
-        result.hasRequest = true;
-        result.request_ = value;
-        return this;
-      }
-
-      public Builder setRequest(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.Builder builderForValue) {
-        result.hasRequest = true;
-        result.request_ = builderForValue.build();
-        return this;
-      }
-
-      public Builder setResponse(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response value) {
-        if (value == null) {
-          throw new NullPointerException();
-        }
-        result.hasResponse = true;
-        result.response_ = value;
-        return this;
-      }
-
-      public Builder setResponse(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.Builder builderForValue) {
-        result.hasResponse = true;
-        result.response_ = builderForValue.build();
-        return this;
-      }
-
-      protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message internalGetResult() {
-        return result;
-      }
-
-      private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message buildParsed()
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        if (!isInitialized()) {
-          throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-        }
-        return buildPartial();
-      }
+    // Use Message.newBuilder() to construct.
+    private Message() {}
+    
+    private static final Message defaultInstance = new Message();
+    public static Message getDefaultInstance() {
+      return defaultInstance;
     }
-
-    public enum MessageType implements
-        com.google.gwt.dev.protobuf.ProtocolMessageEnum {
-      REQUEST(0, 0), RESPONSE(1, 1), ;
-
-      private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<MessageType> internalValueMap = new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<MessageType>() {
-        public MessageType findValueByNumber(int number) {
-          return MessageType.valueOf(number);
+    
+    public Message getDefaultInstanceForType() {
+      return defaultInstance;
+    }
+    
+    public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+        getDescriptor() {
+      return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor;
+    }
+    
+    protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+        internalGetFieldAccessorTable() {
+      return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_fieldAccessorTable;
+    }
+    
+    public enum MessageType
+        implements com.google.gwt.dev.protobuf.ProtocolMessageEnum {
+      REQUEST(0, 0),
+      RESPONSE(1, 1),
+      ;
+      
+      
+      public final int getNumber() { return value; }
+      
+      public static MessageType valueOf(int value) {
+        switch (value) {
+          case 0: return REQUEST;
+          case 1: return RESPONSE;
+          default: return null;
         }
-      };
-
-      private static final MessageType[] VALUES = {REQUEST, RESPONSE,};
-
-      public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptor() {
-        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDescriptor().getEnumTypes().get(
-            0);
       }
-
-      public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<MessageType> internalGetValueMap() {
+      
+      public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<MessageType>
+          internalGetValueMap() {
         return internalValueMap;
       }
-
+      private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<MessageType>
+          internalValueMap =
+            new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<MessageType>() {
+              public MessageType findValueByNumber(int number) {
+                return MessageType.valueOf(number)
+      ;        }
+            };
+      
+      public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor
+          getValueDescriptor() {
+        return getDescriptor().getValues().get(index);
+      }
+      public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+          getDescriptorForType() {
+        return getDescriptor();
+      }
+      public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+          getDescriptor() {
+        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDescriptor().getEnumTypes().get(0);
+      }
+      
+      private static final MessageType[] VALUES = {
+        REQUEST, RESPONSE, 
+      };
       public static MessageType valueOf(
           com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
         if (desc.getType() != getDescriptor()) {
           throw new java.lang.IllegalArgumentException(
-              "EnumValueDescriptor is not for this type.");
+            "EnumValueDescriptor is not for this type.");
         }
         return VALUES[desc.getIndex()];
       }
-
-      public static MessageType valueOf(int value) {
-        switch (value) {
-          case 0:
-            return REQUEST;
-          case 1:
-            return RESPONSE;
-          default:
-            return null;
-        }
-      }
-
       private final int index;
-
       private final int value;
-      static {
-        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-      }
-
       private MessageType(int index, int value) {
         this.index = index;
         this.value = value;
       }
-
-      public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptorForType() {
-        return getDescriptor();
-      }
-
-      public final int getNumber() {
-        return value;
-      }
-
-      public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() {
-        return getDescriptor().getValues().get(index);
+      
+      static {
+        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
       }
     }
+    
     public static final class Request extends
         com.google.gwt.dev.protobuf.GeneratedMessage {
-      public static final class Builder extends
-          com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-        private static Builder create() {
-          Builder builder = new Builder();
-          builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request();
-          return builder;
-        }
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request result;
-
-        // Construct using
-        // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.newBuilder()
-        private Builder() {
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request build() {
-          if (result != null && !isInitialized()) {
-            throw newUninitializedMessageException(result);
-          }
-          return buildPartial();
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request buildPartial() {
-          if (result == null) {
-            throw new IllegalStateException(
-                "build() has already been called on this Builder.");
-          }
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request returnMe = result;
-          result = null;
-          return returnMe;
-        }
-
-        public Builder clear() {
-          if (result == null) {
-            throw new IllegalStateException(
-                "Cannot call clear() after build().");
-          }
-          result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request();
-          return this;
-        }
-
-        public Builder clearDevModeRequest() {
-          result.hasDevModeRequest = false;
-          result.devModeRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance();
-          return this;
-        }
-
-        public Builder clearRequestId() {
-          result.hasRequestId = false;
-          result.requestId_ = 0;
-          return this;
-        }
-
-        public Builder clearServiceType() {
-          result.hasServiceType = false;
-          result.serviceType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType.VIEWER;
-          return this;
-        }
-
-        public Builder clearViewerRequest() {
-          result.hasViewerRequest = false;
-          result.viewerRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance();
-          return this;
-        }
-
-        public Builder clone() {
-          return create().mergeFrom(result);
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request getDefaultInstanceForType() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance();
-        }
-
-        public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDescriptor();
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest getDevModeRequest() {
-          return result.getDevModeRequest();
-        }
-
-        public int getRequestId() {
-          return result.getRequestId();
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType getServiceType() {
-          return result.getServiceType();
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest getViewerRequest() {
-          return result.getViewerRequest();
-        }
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest
-        // devModeRequest = 4;
-        public boolean hasDevModeRequest() {
-          return result.hasDevModeRequest();
-        }
-
-        // optional uint32 requestId = 2;
-        public boolean hasRequestId() {
-          return result.hasRequestId();
-        }
-
-        // required
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ServiceType
-        // serviceType = 1;
-        public boolean hasServiceType() {
-          return result.hasServiceType();
-        }
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest
-        // viewerRequest = 3;
-        public boolean hasViewerRequest() {
-          return result.hasViewerRequest();
-        }
-
-        public boolean isInitialized() {
-          return result.isInitialized();
-        }
-
-        public Builder mergeDevModeRequest(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest value) {
-          if (result.hasDevModeRequest()
-              && result.devModeRequest_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance()) {
-            result.devModeRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.newBuilder(
-                result.devModeRequest_).mergeFrom(value).buildPartial();
-          } else {
-            result.devModeRequest_ = value;
-          }
-          result.hasDevModeRequest = true;
-          return this;
-        }
-
-        public Builder mergeFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-          while (true) {
-            int tag = input.readTag();
-            switch (tag) {
-              case 0:
-                this.setUnknownFields(unknownFields.build());
-                return this;
-              default: {
-                if (!parseUnknownField(input, unknownFields, extensionRegistry,
-                    tag)) {
-                  this.setUnknownFields(unknownFields.build());
-                  return this;
-                }
-                break;
-              }
-              case 8: {
-                int rawValue = input.readEnum();
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType.valueOf(rawValue);
-                if (value == null) {
-                  unknownFields.mergeVarintField(1, rawValue);
-                } else {
-                  setServiceType(value);
-                }
-                break;
-              }
-              case 16: {
-                setRequestId(input.readUInt32());
-                break;
-              }
-              case 26: {
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.newBuilder();
-                if (hasViewerRequest()) {
-                  subBuilder.mergeFrom(getViewerRequest());
-                }
-                input.readMessage(subBuilder, extensionRegistry);
-                setViewerRequest(subBuilder.buildPartial());
-                break;
-              }
-              case 34: {
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.newBuilder();
-                if (hasDevModeRequest()) {
-                  subBuilder.mergeFrom(getDevModeRequest());
-                }
-                input.readMessage(subBuilder, extensionRegistry);
-                setDevModeRequest(subBuilder.buildPartial());
-                break;
-              }
-            }
-          }
-        }
-
-        public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-          if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request) {
-            return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request) other);
-          } else {
-            super.mergeFrom(other);
-            return this;
-          }
-        }
-
-        public Builder mergeFrom(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request other) {
-          if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance())
-            return this;
-          if (other.hasServiceType()) {
-            setServiceType(other.getServiceType());
-          }
-          if (other.hasRequestId()) {
-            setRequestId(other.getRequestId());
-          }
-          if (other.hasViewerRequest()) {
-            mergeViewerRequest(other.getViewerRequest());
-          }
-          if (other.hasDevModeRequest()) {
-            mergeDevModeRequest(other.getDevModeRequest());
-          }
-          this.mergeUnknownFields(other.getUnknownFields());
-          return this;
-        }
-
-        public Builder mergeViewerRequest(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest value) {
-          if (result.hasViewerRequest()
-              && result.viewerRequest_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance()) {
-            result.viewerRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.newBuilder(
-                result.viewerRequest_).mergeFrom(value).buildPartial();
-          } else {
-            result.viewerRequest_ = value;
-          }
-          result.hasViewerRequest = true;
-          return this;
-        }
-
-        public Builder setDevModeRequest(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest value) {
-          if (value == null) {
-            throw new NullPointerException();
-          }
-          result.hasDevModeRequest = true;
-          result.devModeRequest_ = value;
-          return this;
-        }
-
-        public Builder setDevModeRequest(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.Builder builderForValue) {
-          result.hasDevModeRequest = true;
-          result.devModeRequest_ = builderForValue.build();
-          return this;
-        }
-
-        public Builder setRequestId(int value) {
-          result.hasRequestId = true;
-          result.requestId_ = value;
-          return this;
-        }
-
-        public Builder setServiceType(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType value) {
-          if (value == null) {
-            throw new NullPointerException();
-          }
-          result.hasServiceType = true;
-          result.serviceType_ = value;
-          return this;
-        }
-
-        public Builder setViewerRequest(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest value) {
-          if (value == null) {
-            throw new NullPointerException();
-          }
-          result.hasViewerRequest = true;
-          result.viewerRequest_ = value;
-          return this;
-        }
-
-        public Builder setViewerRequest(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Builder builderForValue) {
-          result.hasViewerRequest = true;
-          result.viewerRequest_ = builderForValue.build();
-          return this;
-        }
-
-        protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request internalGetResult() {
-          return result;
-        }
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request buildParsed()
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          if (!isInitialized()) {
-            throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-          }
-          return buildPartial();
-        }
+      // Use Request.newBuilder() to construct.
+      private Request() {}
+      
+      private static final Request defaultInstance = new Request();
+      public static Request getDefaultInstance() {
+        return defaultInstance;
       }
-
-      public static final class DevModeRequest extends
-          com.google.gwt.dev.protobuf.GeneratedMessage {
-        public static final class Builder extends
-            com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-          private static Builder create() {
-            Builder builder = new Builder();
-            builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest();
-            return builder;
-          }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest result;
-
-          // Construct using
-          // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.newBuilder()
-          private Builder() {
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest build() {
-            if (result != null && !isInitialized()) {
-              throw newUninitializedMessageException(result);
-            }
-            return buildPartial();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest buildPartial() {
-            if (result == null) {
-              throw new IllegalStateException(
-                  "build() has already been called on this Builder.");
-            }
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest returnMe = result;
-            result = null;
-            return returnMe;
-          }
-
-          public Builder clear() {
-            if (result == null) {
-              throw new IllegalStateException(
-                  "Cannot call clear() after build().");
-            }
-            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest();
-            return this;
-          }
-
-          public Builder clearCapabilityExchange() {
-            result.hasCapabilityExchange = false;
-            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearRequestType() {
-            result.hasRequestType = false;
-            result.requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
-            return this;
-          }
-
-          public Builder clearRestartWebServer() {
-            result.hasRestartWebServer = false;
-            result.restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clone() {
-            return create().mergeFrom(result);
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange getCapabilityExchange() {
-            return result.getCapabilityExchange();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest getDefaultInstanceForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance();
-          }
-
-          public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDescriptor();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getRequestType() {
-            return result.getRequestType();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer getRestartWebServer() {
-            return result.getRestartWebServer();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.CapabilityExchange
-          // capabilityExchange = 2;
-          public boolean hasCapabilityExchange() {
-            return result.hasCapabilityExchange();
-          }
-
-          // required
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType
-          // requestType = 1;
-          public boolean hasRequestType() {
-            return result.hasRequestType();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RestartWebServer
-          // restartWebServer = 3;
-          public boolean hasRestartWebServer() {
-            return result.hasRestartWebServer();
-          }
-
-          public boolean isInitialized() {
-            return result.isInitialized();
-          }
-
-          public Builder mergeCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange value) {
-            if (result.hasCapabilityExchange()
-                && result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance()) {
-              result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.newBuilder(
-                  result.capabilityExchange_).mergeFrom(value).buildPartial();
-            } else {
-              result.capabilityExchange_ = value;
-            }
-            result.hasCapabilityExchange = true;
-            return this;
-          }
-
-          public Builder mergeFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-            while (true) {
-              int tag = input.readTag();
-              switch (tag) {
-                case 0:
-                  this.setUnknownFields(unknownFields.build());
-                  return this;
-                default: {
-                  if (!parseUnknownField(input, unknownFields,
-                      extensionRegistry, tag)) {
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  }
-                  break;
-                }
-                case 8: {
-                  int rawValue = input.readEnum();
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.valueOf(rawValue);
-                  if (value == null) {
-                    unknownFields.mergeVarintField(1, rawValue);
-                  } else {
-                    setRequestType(value);
-                  }
-                  break;
-                }
-                case 18: {
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.newBuilder();
-                  if (hasCapabilityExchange()) {
-                    subBuilder.mergeFrom(getCapabilityExchange());
-                  }
-                  input.readMessage(subBuilder, extensionRegistry);
-                  setCapabilityExchange(subBuilder.buildPartial());
-                  break;
-                }
-                case 26: {
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.newBuilder();
-                  if (hasRestartWebServer()) {
-                    subBuilder.mergeFrom(getRestartWebServer());
-                  }
-                  input.readMessage(subBuilder, extensionRegistry);
-                  setRestartWebServer(subBuilder.buildPartial());
-                  break;
-                }
-              }
-            }
-          }
-
-          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest) {
-              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest) other);
-            } else {
-              super.mergeFrom(other);
-              return this;
-            }
-          }
-
-          public Builder mergeFrom(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest other) {
-            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance())
-              return this;
-            if (other.hasRequestType()) {
-              setRequestType(other.getRequestType());
-            }
-            if (other.hasCapabilityExchange()) {
-              mergeCapabilityExchange(other.getCapabilityExchange());
-            }
-            if (other.hasRestartWebServer()) {
-              mergeRestartWebServer(other.getRestartWebServer());
-            }
-            this.mergeUnknownFields(other.getUnknownFields());
-            return this;
-          }
-
-          public Builder mergeRestartWebServer(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer value) {
-            if (result.hasRestartWebServer()
-                && result.restartWebServer_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance()) {
-              result.restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.newBuilder(
-                  result.restartWebServer_).mergeFrom(value).buildPartial();
-            } else {
-              result.restartWebServer_ = value;
-            }
-            result.hasRestartWebServer = true;
-            return this;
-          }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = value;
-            return this;
-          }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.Builder builderForValue) {
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setRequestType(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasRequestType = true;
-            result.requestType_ = value;
-            return this;
-          }
-
-          public Builder setRestartWebServer(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasRestartWebServer = true;
-            result.restartWebServer_ = value;
-            return this;
-          }
-
-          public Builder setRestartWebServer(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.Builder builderForValue) {
-            result.hasRestartWebServer = true;
-            result.restartWebServer_ = builderForValue.build();
-            return this;
-          }
-
-          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest internalGetResult() {
-            return result;
-          }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest buildParsed()
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            if (!isInitialized()) {
-              throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-            }
-            return buildPartial();
-          }
-        }
-
-        public static final class CapabilityExchange extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
-          public static final class Builder extends
-              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-            private static Builder create() {
-              Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange();
-              return builder;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.newBuilder()
-            private Builder() {
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange build() {
-              if (result != null && !isInitialized()) {
-                throw newUninitializedMessageException(result);
-              }
-              return buildPartial();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange buildPartial() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
-              }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange returnMe = result;
-              result = null;
-              return returnMe;
-            }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
-              }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange();
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDescriptor();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-              while (true) {
-                int tag = input.readTag();
-                switch (tag) {
-                  case 0:
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  default: {
-                    if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    }
-                    break;
-                  }
-                }
-              }
-            }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance())
-                return this;
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
-            }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
-            }
-
-          }
-
-          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static CapabilityExchange getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private int memoizedSerializedSize = -1;
-
-          // Use CapabilityExchange.newBuilder() to construct.
-          private CapabilityExchange() {
-          }
-
-          public CapabilityExchange getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public final boolean isInitialized() {
-            return true;
-          }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            getUnknownFields().writeTo(output);
-          }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_fieldAccessorTable;
-          }
-        }
-        public enum RequestType implements
-            com.google.gwt.dev.protobuf.ProtocolMessageEnum {
-          CAPABILITY_EXCHANGE(0, 0), RESTART_WEB_SERVER(1, 1), ;
-
-          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType> internalValueMap = new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>() {
-            public RequestType findValueByNumber(int number) {
-              return RequestType.valueOf(number);
-            }
-          };
-
-          private static final RequestType[] VALUES = {
-              CAPABILITY_EXCHANGE, RESTART_WEB_SERVER,};
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDescriptor().getEnumTypes().get(
-                0);
-          }
-
-          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType> internalGetValueMap() {
-            return internalValueMap;
-          }
-
-          public static RequestType valueOf(
-              com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
-            if (desc.getType() != getDescriptor()) {
-              throw new java.lang.IllegalArgumentException(
-                  "EnumValueDescriptor is not for this type.");
-            }
-            return VALUES[desc.getIndex()];
-          }
-
-          public static RequestType valueOf(int value) {
-            switch (value) {
-              case 0:
-                return CAPABILITY_EXCHANGE;
-              case 1:
-                return RESTART_WEB_SERVER;
-              default:
-                return null;
-            }
-          }
-
-          private final int index;
-
-          private final int value;
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          private RequestType(int index, int value) {
-            this.index = index;
-            this.value = value;
-          }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptorForType() {
-            return getDescriptor();
-          }
-
-          public final int getNumber() {
-            return value;
-          }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() {
-            return getDescriptor().getValues().get(index);
-          }
-        }
-
-        public static final class RestartWebServer extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
-          public static final class Builder extends
-              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-            private static Builder create() {
-              Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer();
-              return builder;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.newBuilder()
-            private Builder() {
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer build() {
-              if (result != null && !isInitialized()) {
-                throw newUninitializedMessageException(result);
-              }
-              return buildPartial();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer buildPartial() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
-              }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer returnMe = result;
-              result = null;
-              return returnMe;
-            }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
-              }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer();
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDescriptor();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-              while (true) {
-                int tag = input.readTag();
-                switch (tag) {
-                  case 0:
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  default: {
-                    if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    }
-                    break;
-                  }
-                }
-              }
-            }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance())
-                return this;
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
-            }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
-            }
-
-          }
-
-          private static final RestartWebServer defaultInstance = new RestartWebServer();
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static RestartWebServer getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private int memoizedSerializedSize = -1;
-
-          // Use RestartWebServer.newBuilder() to construct.
-          private RestartWebServer() {
-          }
-
-          public RestartWebServer getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public final boolean isInitialized() {
-            return true;
-          }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            getUnknownFields().writeTo(output);
-          }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_fieldAccessorTable;
-          }
-        }
-
-        private static final DevModeRequest defaultInstance = new DevModeRequest();
-
-        // required
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType
-        // requestType = 1;
-        public static final int REQUESTTYPE_FIELD_NUMBER = 1;
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-        }
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-        }
-
-        public static DevModeRequest getDefaultInstance() {
-          return defaultInstance;
-        }
-
-        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor;
-        }
-
-        public static Builder newBuilder() {
-          return Builder.create();
-        }
-
-        public static Builder newBuilder(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest prototype) {
-          return newBuilder().mergeFrom(prototype);
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseDelimitedFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseDelimitedFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            byte[] data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            byte[] data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
-        private boolean hasRequestType;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.CapabilityExchange
-        // capabilityExchange = 2;
-        public static final int CAPABILITYEXCHANGE_FIELD_NUMBER = 2;
-
-        private boolean hasCapabilityExchange;
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance();
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RestartWebServer
-        // restartWebServer = 3;
-        public static final int RESTARTWEBSERVER_FIELD_NUMBER = 3;
-
-        private boolean hasRestartWebServer;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance();
-        private int memoizedSerializedSize = -1;
-
-        // Use DevModeRequest.newBuilder() to construct.
-        private DevModeRequest() {
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange getCapabilityExchange() {
-          return capabilityExchange_;
-        }
-
-        public DevModeRequest getDefaultInstanceForType() {
-          return defaultInstance;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getRequestType() {
-          return requestType_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer getRestartWebServer() {
-          return restartWebServer_;
-        }
-
-        public int getSerializedSize() {
-          int size = memoizedSerializedSize;
-          if (size != -1)
-            return size;
-
-          size = 0;
-          if (hasRequestType()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-                1, getRequestType().getNumber());
-          }
-          if (hasCapabilityExchange()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                2, getCapabilityExchange());
-          }
-          if (hasRestartWebServer()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                3, getRestartWebServer());
-          }
-          size += getUnknownFields().getSerializedSize();
-          memoizedSerializedSize = size;
-          return size;
-        }
-
-        public boolean hasCapabilityExchange() {
-          return hasCapabilityExchange;
-        }
-
-        public boolean hasRequestType() {
-          return hasRequestType;
-        }
-
-        public boolean hasRestartWebServer() {
-          return hasRestartWebServer;
-        }
-
-        public final boolean isInitialized() {
-          if (!hasRequestType)
-            return false;
-          return true;
-        }
-
-        public Builder newBuilderForType() {
-          return newBuilder();
-        }
-
-        public Builder toBuilder() {
-          return newBuilder(this);
-        }
-
-        public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
-            throws java.io.IOException {
-          if (hasRequestType()) {
-            output.writeEnum(1, getRequestType().getNumber());
-          }
-          if (hasCapabilityExchange()) {
-            output.writeMessage(2, getCapabilityExchange());
-          }
-          if (hasRestartWebServer()) {
-            output.writeMessage(3, getRestartWebServer());
-          }
-          getUnknownFields().writeTo(output);
-        }
-
-        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_fieldAccessorTable;
-        }
+      
+      public Request getDefaultInstanceForType() {
+        return defaultInstance;
       }
-      public enum ServiceType implements
-          com.google.gwt.dev.protobuf.ProtocolMessageEnum {
-        VIEWER(0, 0), DEV_MODE(1, 1), ;
-
-        private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ServiceType> internalValueMap = new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ServiceType>() {
-          public ServiceType findValueByNumber(int number) {
-            return ServiceType.valueOf(number);
+      
+      public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+          getDescriptor() {
+        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor;
+      }
+      
+      protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+          internalGetFieldAccessorTable() {
+        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_fieldAccessorTable;
+      }
+      
+      public enum ServiceType
+          implements com.google.gwt.dev.protobuf.ProtocolMessageEnum {
+        VIEWER(0, 0),
+        DEV_MODE(1, 1),
+        ;
+        
+        
+        public final int getNumber() { return value; }
+        
+        public static ServiceType valueOf(int value) {
+          switch (value) {
+            case 0: return VIEWER;
+            case 1: return DEV_MODE;
+            default: return null;
           }
-        };
-
-        private static final ServiceType[] VALUES = {VIEWER, DEV_MODE,};
-
-        public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptor() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDescriptor().getEnumTypes().get(
-              0);
         }
-
-        public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ServiceType> internalGetValueMap() {
+        
+        public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ServiceType>
+            internalGetValueMap() {
           return internalValueMap;
         }
-
+        private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ServiceType>
+            internalValueMap =
+              new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ServiceType>() {
+                public ServiceType findValueByNumber(int number) {
+                  return ServiceType.valueOf(number)
+        ;        }
+              };
+        
+        public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor
+            getValueDescriptor() {
+          return getDescriptor().getValues().get(index);
+        }
+        public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+            getDescriptorForType() {
+          return getDescriptor();
+        }
+        public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+            getDescriptor() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDescriptor().getEnumTypes().get(0);
+        }
+        
+        private static final ServiceType[] VALUES = {
+          VIEWER, DEV_MODE, 
+        };
         public static ServiceType valueOf(
             com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
           if (desc.getType() != getDescriptor()) {
             throw new java.lang.IllegalArgumentException(
-                "EnumValueDescriptor is not for this type.");
+              "EnumValueDescriptor is not for this type.");
           }
           return VALUES[desc.getIndex()];
         }
-
-        public static ServiceType valueOf(int value) {
-          switch (value) {
-            case 0:
-              return VIEWER;
-            case 1:
-              return DEV_MODE;
-            default:
-              return null;
-          }
-        }
-
         private final int index;
-
         private final int value;
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-        }
-
         private ServiceType(int index, int value) {
           this.index = index;
           this.value = value;
         }
-
-        public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptorForType() {
-          return getDescriptor();
-        }
-
-        public final int getNumber() {
-          return value;
-        }
-
-        public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() {
-          return getDescriptor().getValues().get(index);
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
         }
       }
-
+      
       public static final class ViewerRequest extends
           com.google.gwt.dev.protobuf.GeneratedMessage {
-        public static final class AddLog extends
+        // Use ViewerRequest.newBuilder() to construct.
+        private ViewerRequest() {}
+        
+        private static final ViewerRequest defaultInstance = new ViewerRequest();
+        public static ViewerRequest getDefaultInstance() {
+          return defaultInstance;
+        }
+        
+        public ViewerRequest getDefaultInstanceForType() {
+          return defaultInstance;
+        }
+        
+        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+            getDescriptor() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor;
+        }
+        
+        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+            internalGetFieldAccessorTable() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_fieldAccessorTable;
+        }
+        
+        public enum RequestType
+            implements com.google.gwt.dev.protobuf.ProtocolMessageEnum {
+          CAPABILITY_EXCHANGE(0, 0),
+          ADD_LOG(1, 1),
+          ADD_LOG_BRANCH(2, 2),
+          ADD_LOG_ENTRY(3, 3),
+          DISCONNECT_LOG(4, 4),
+          INITIALIZE(5, 5),
+          ;
+          
+          
+          public final int getNumber() { return value; }
+          
+          public static RequestType valueOf(int value) {
+            switch (value) {
+              case 0: return CAPABILITY_EXCHANGE;
+              case 1: return ADD_LOG;
+              case 2: return ADD_LOG_BRANCH;
+              case 3: return ADD_LOG_ENTRY;
+              case 4: return DISCONNECT_LOG;
+              case 5: return INITIALIZE;
+              default: return null;
+            }
+          }
+          
+          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>
+              internalGetValueMap() {
+            return internalValueMap;
+          }
+          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>
+              internalValueMap =
+                new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>() {
+                  public RequestType findValueByNumber(int number) {
+                    return RequestType.valueOf(number)
+          ;        }
+                };
+          
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor
+              getValueDescriptor() {
+            return getDescriptor().getValues().get(index);
+          }
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptorForType() {
+            return getDescriptor();
+          }
+          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDescriptor().getEnumTypes().get(0);
+          }
+          
+          private static final RequestType[] VALUES = {
+            CAPABILITY_EXCHANGE, ADD_LOG, ADD_LOG_BRANCH, ADD_LOG_ENTRY, DISCONNECT_LOG, INITIALIZE, 
+          };
+          public static RequestType valueOf(
+              com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
+            if (desc.getType() != getDescriptor()) {
+              throw new java.lang.IllegalArgumentException(
+                "EnumValueDescriptor is not for this type.");
+            }
+            return VALUES[desc.getIndex()];
+          }
+          private final int index;
+          private final int value;
+          private RequestType(int index, int value) {
+            this.index = index;
+            this.value = value;
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+        }
+        
+        public static final class CapabilityExchange extends
             com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use CapabilityExchange.newBuilder() to construct.
+          private CapabilityExchange() {}
+          
+          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
+          public static CapabilityExchange getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public CapabilityExchange getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_fieldAccessorTable;
+          }
+          
+          public final boolean isInitialized() {
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
+          }
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
           public static final class Builder extends
               com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange();
+              return builder;
+            }
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange internalGetResult() {
+              return result;
+            }
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance()) return this;
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                }
+              }
+            }
+            
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+          }
+        }
+        
+        public static final class AddLog extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use AddLog.newBuilder() to construct.
+          private AddLog() {}
+          
+          private static final AddLog defaultInstance = new AddLog();
+          public static AddLog getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public AddLog getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_fieldAccessorTable;
+          }
+          
+          public enum LogType
+              implements com.google.gwt.dev.protobuf.ProtocolMessageEnum {
+            MAIN(0, 0),
+            MODULE(1, 1),
+            WEB_SERVER(2, 2),
+            ;
+            
+            
+            public final int getNumber() { return value; }
+            
+            public static LogType valueOf(int value) {
+              switch (value) {
+                case 0: return MAIN;
+                case 1: return MODULE;
+                case 2: return WEB_SERVER;
+                default: return null;
+              }
+            }
+            
+            public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<LogType>
+                internalGetValueMap() {
+              return internalValueMap;
+            }
+            private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<LogType>
+                internalValueMap =
+                  new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<LogType>() {
+                    public LogType findValueByNumber(int number) {
+                      return LogType.valueOf(number)
+            ;        }
+                  };
+            
+            public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor
+                getValueDescriptor() {
+              return getDescriptor().getValues().get(index);
+            }
+            public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+                getDescriptorForType() {
+              return getDescriptor();
+            }
+            public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+                getDescriptor() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDescriptor().getEnumTypes().get(0);
+            }
+            
+            private static final LogType[] VALUES = {
+              MAIN, MODULE, WEB_SERVER, 
+            };
+            public static LogType valueOf(
+                com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
+              if (desc.getType() != getDescriptor()) {
+                throw new java.lang.IllegalArgumentException(
+                  "EnumValueDescriptor is not for this type.");
+              }
+              return VALUES[desc.getIndex()];
+            }
+            private final int index;
+            private final int value;
+            private LogType(int index, int value) {
+              this.index = index;
+              this.value = value;
+            }
+            
+            static {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+            }
+          }
+          
+          public static final class ModuleLog extends
+              com.google.gwt.dev.protobuf.GeneratedMessage {
+            // Use ModuleLog.newBuilder() to construct.
+            private ModuleLog() {}
+            
+            private static final ModuleLog defaultInstance = new ModuleLog();
+            public static ModuleLog getDefaultInstance() {
+              return defaultInstance;
+            }
+            
+            public ModuleLog getDefaultInstanceForType() {
+              return defaultInstance;
+            }
+            
+            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptor() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor;
+            }
+            
+            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+                internalGetFieldAccessorTable() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_fieldAccessorTable;
+            }
+            
+            // required string name = 1;
+            public static final int NAME_FIELD_NUMBER = 1;
+            private boolean hasName;
+            private java.lang.String name_ = "";
+            public boolean hasName() { return hasName; }
+            public java.lang.String getName() { return name_; }
+            
+            // optional bytes icon = 2;
+            public static final int ICON_FIELD_NUMBER = 2;
+            private boolean hasIcon;
+            private com.google.gwt.dev.protobuf.ByteString icon_ = com.google.gwt.dev.protobuf.ByteString.EMPTY;
+            public boolean hasIcon() { return hasIcon; }
+            public com.google.gwt.dev.protobuf.ByteString getIcon() { return icon_; }
+            
+            // optional string sessionKey = 3;
+            public static final int SESSIONKEY_FIELD_NUMBER = 3;
+            private boolean hasSessionKey;
+            private java.lang.String sessionKey_ = "";
+            public boolean hasSessionKey() { return hasSessionKey; }
+            public java.lang.String getSessionKey() { return sessionKey_; }
+            
+            // optional string userAgent = 4;
+            public static final int USERAGENT_FIELD_NUMBER = 4;
+            private boolean hasUserAgent;
+            private java.lang.String userAgent_ = "";
+            public boolean hasUserAgent() { return hasUserAgent; }
+            public java.lang.String getUserAgent() { return userAgent_; }
+            
+            // optional string url = 5;
+            public static final int URL_FIELD_NUMBER = 5;
+            private boolean hasUrl;
+            private java.lang.String url_ = "";
+            public boolean hasUrl() { return hasUrl; }
+            public java.lang.String getUrl() { return url_; }
+            
+            // optional string tabKey = 6;
+            public static final int TABKEY_FIELD_NUMBER = 6;
+            private boolean hasTabKey;
+            private java.lang.String tabKey_ = "";
+            public boolean hasTabKey() { return hasTabKey; }
+            public java.lang.String getTabKey() { return tabKey_; }
+            
+            // optional string remoteHost = 7;
+            public static final int REMOTEHOST_FIELD_NUMBER = 7;
+            private boolean hasRemoteHost;
+            private java.lang.String remoteHost_ = "";
+            public boolean hasRemoteHost() { return hasRemoteHost; }
+            public java.lang.String getRemoteHost() { return remoteHost_; }
+            
+            public final boolean isInitialized() {
+              if (!hasName) return false;
+              return true;
+            }
+            
+            public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                                throws java.io.IOException {
+              if (hasName()) {
+                output.writeString(1, getName());
+              }
+              if (hasIcon()) {
+                output.writeBytes(2, getIcon());
+              }
+              if (hasSessionKey()) {
+                output.writeString(3, getSessionKey());
+              }
+              if (hasUserAgent()) {
+                output.writeString(4, getUserAgent());
+              }
+              if (hasUrl()) {
+                output.writeString(5, getUrl());
+              }
+              if (hasTabKey()) {
+                output.writeString(6, getTabKey());
+              }
+              if (hasRemoteHost()) {
+                output.writeString(7, getRemoteHost());
+              }
+              getUnknownFields().writeTo(output);
+            }
+            
+            private int memoizedSerializedSize = -1;
+            public int getSerializedSize() {
+              int size = memoizedSerializedSize;
+              if (size != -1) return size;
+            
+              size = 0;
+              if (hasName()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(1, getName());
+              }
+              if (hasIcon()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeBytesSize(2, getIcon());
+              }
+              if (hasSessionKey()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(3, getSessionKey());
+              }
+              if (hasUserAgent()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(4, getUserAgent());
+              }
+              if (hasUrl()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(5, getUrl());
+              }
+              if (hasTabKey()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(6, getTabKey());
+              }
+              if (hasRemoteHost()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(7, getRemoteHost());
+              }
+              size += getUnknownFields().getSerializedSize();
+              memoizedSerializedSize = size;
+              return size;
+            }
+            
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(byte[] data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
+                byte[] data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseDelimitedFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseDelimitedFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            
+            public static Builder newBuilder() { return Builder.create(); }
+            public Builder newBuilderForType() { return newBuilder(); }
+            public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog prototype) {
+              return newBuilder().mergeFrom(prototype);
+            }
+            public Builder toBuilder() { return newBuilder(this); }
+            
+            public static final class Builder extends
+                com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog result;
+              
+              // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.newBuilder()
+              private Builder() {}
+              
+              private static Builder create() {
+                Builder builder = new Builder();
+                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog();
+                return builder;
+              }
+              
+              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog internalGetResult() {
+                return result;
+              }
+              
+              public Builder clear() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "Cannot call clear() after build().");
+                }
+                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog();
+                return this;
+              }
+              
+              public Builder clone() {
+                return create().mergeFrom(result);
+              }
+              
+              public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                  getDescriptorForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDescriptor();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog getDefaultInstanceForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance();
+              }
+              
+              public boolean isInitialized() {
+                return result.isInitialized();
+              }
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog build() {
+                if (result != null && !isInitialized()) {
+                  throw newUninitializedMessageException(result);
+                }
+                return buildPartial();
+              }
+              
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog buildParsed()
+                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+                if (!isInitialized()) {
+                  throw newUninitializedMessageException(
+                    result).asInvalidProtocolBufferException();
+                }
+                return buildPartial();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog buildPartial() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "build() has already been called on this Builder.");
+                }
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog returnMe = result;
+                result = null;
+                return returnMe;
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog) {
+                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog)other);
+                } else {
+                  super.mergeFrom(other);
+                  return this;
+                }
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog other) {
+                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance()) return this;
+                if (other.hasName()) {
+                  setName(other.getName());
+                }
+                if (other.hasIcon()) {
+                  setIcon(other.getIcon());
+                }
+                if (other.hasSessionKey()) {
+                  setSessionKey(other.getSessionKey());
+                }
+                if (other.hasUserAgent()) {
+                  setUserAgent(other.getUserAgent());
+                }
+                if (other.hasUrl()) {
+                  setUrl(other.getUrl());
+                }
+                if (other.hasTabKey()) {
+                  setTabKey(other.getTabKey());
+                }
+                if (other.hasRemoteHost()) {
+                  setRemoteHost(other.getRemoteHost());
+                }
+                this.mergeUnknownFields(other.getUnknownFields());
+                return this;
+              }
+              
+              public Builder mergeFrom(
+                  com.google.gwt.dev.protobuf.CodedInputStream input,
+                  com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                  throws java.io.IOException {
+                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                  com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                    this.getUnknownFields());
+                while (true) {
+                  int tag = input.readTag();
+                  switch (tag) {
+                    case 0:
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    default: {
+                      if (!parseUnknownField(input, unknownFields,
+                                             extensionRegistry, tag)) {
+                        this.setUnknownFields(unknownFields.build());
+                        return this;
+                      }
+                      break;
+                    }
+                    case 10: {
+                      setName(input.readString());
+                      break;
+                    }
+                    case 18: {
+                      setIcon(input.readBytes());
+                      break;
+                    }
+                    case 26: {
+                      setSessionKey(input.readString());
+                      break;
+                    }
+                    case 34: {
+                      setUserAgent(input.readString());
+                      break;
+                    }
+                    case 42: {
+                      setUrl(input.readString());
+                      break;
+                    }
+                    case 50: {
+                      setTabKey(input.readString());
+                      break;
+                    }
+                    case 58: {
+                      setRemoteHost(input.readString());
+                      break;
+                    }
+                  }
+                }
+              }
+              
+              
+              // required string name = 1;
+              public boolean hasName() {
+                return result.hasName();
+              }
+              public java.lang.String getName() {
+                return result.getName();
+              }
+              public Builder setName(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasName = true;
+                result.name_ = value;
+                return this;
+              }
+              public Builder clearName() {
+                result.hasName = false;
+                result.name_ = getDefaultInstance().getName();
+                return this;
+              }
+              
+              // optional bytes icon = 2;
+              public boolean hasIcon() {
+                return result.hasIcon();
+              }
+              public com.google.gwt.dev.protobuf.ByteString getIcon() {
+                return result.getIcon();
+              }
+              public Builder setIcon(com.google.gwt.dev.protobuf.ByteString value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasIcon = true;
+                result.icon_ = value;
+                return this;
+              }
+              public Builder clearIcon() {
+                result.hasIcon = false;
+                result.icon_ = getDefaultInstance().getIcon();
+                return this;
+              }
+              
+              // optional string sessionKey = 3;
+              public boolean hasSessionKey() {
+                return result.hasSessionKey();
+              }
+              public java.lang.String getSessionKey() {
+                return result.getSessionKey();
+              }
+              public Builder setSessionKey(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasSessionKey = true;
+                result.sessionKey_ = value;
+                return this;
+              }
+              public Builder clearSessionKey() {
+                result.hasSessionKey = false;
+                result.sessionKey_ = getDefaultInstance().getSessionKey();
+                return this;
+              }
+              
+              // optional string userAgent = 4;
+              public boolean hasUserAgent() {
+                return result.hasUserAgent();
+              }
+              public java.lang.String getUserAgent() {
+                return result.getUserAgent();
+              }
+              public Builder setUserAgent(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasUserAgent = true;
+                result.userAgent_ = value;
+                return this;
+              }
+              public Builder clearUserAgent() {
+                result.hasUserAgent = false;
+                result.userAgent_ = getDefaultInstance().getUserAgent();
+                return this;
+              }
+              
+              // optional string url = 5;
+              public boolean hasUrl() {
+                return result.hasUrl();
+              }
+              public java.lang.String getUrl() {
+                return result.getUrl();
+              }
+              public Builder setUrl(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasUrl = true;
+                result.url_ = value;
+                return this;
+              }
+              public Builder clearUrl() {
+                result.hasUrl = false;
+                result.url_ = getDefaultInstance().getUrl();
+                return this;
+              }
+              
+              // optional string tabKey = 6;
+              public boolean hasTabKey() {
+                return result.hasTabKey();
+              }
+              public java.lang.String getTabKey() {
+                return result.getTabKey();
+              }
+              public Builder setTabKey(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasTabKey = true;
+                result.tabKey_ = value;
+                return this;
+              }
+              public Builder clearTabKey() {
+                result.hasTabKey = false;
+                result.tabKey_ = getDefaultInstance().getTabKey();
+                return this;
+              }
+              
+              // optional string remoteHost = 7;
+              public boolean hasRemoteHost() {
+                return result.hasRemoteHost();
+              }
+              public java.lang.String getRemoteHost() {
+                return result.getRemoteHost();
+              }
+              public Builder setRemoteHost(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasRemoteHost = true;
+                result.remoteHost_ = value;
+                return this;
+              }
+              public Builder clearRemoteHost() {
+                result.hasRemoteHost = false;
+                result.remoteHost_ = getDefaultInstance().getRemoteHost();
+                return this;
+              }
+            }
+            
+            static {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+            }
+            
+            static {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+            }
+          }
+          
+          public static final class ServerLog extends
+              com.google.gwt.dev.protobuf.GeneratedMessage {
+            // Use ServerLog.newBuilder() to construct.
+            private ServerLog() {}
+            
+            private static final ServerLog defaultInstance = new ServerLog();
+            public static ServerLog getDefaultInstance() {
+              return defaultInstance;
+            }
+            
+            public ServerLog getDefaultInstanceForType() {
+              return defaultInstance;
+            }
+            
+            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptor() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor;
+            }
+            
+            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+                internalGetFieldAccessorTable() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_fieldAccessorTable;
+            }
+            
+            // required string name = 1;
+            public static final int NAME_FIELD_NUMBER = 1;
+            private boolean hasName;
+            private java.lang.String name_ = "";
+            public boolean hasName() { return hasName; }
+            public java.lang.String getName() { return name_; }
+            
+            // optional bytes icon = 2;
+            public static final int ICON_FIELD_NUMBER = 2;
+            private boolean hasIcon;
+            private com.google.gwt.dev.protobuf.ByteString icon_ = com.google.gwt.dev.protobuf.ByteString.EMPTY;
+            public boolean hasIcon() { return hasIcon; }
+            public com.google.gwt.dev.protobuf.ByteString getIcon() { return icon_; }
+            
+            public final boolean isInitialized() {
+              if (!hasName) return false;
+              return true;
+            }
+            
+            public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                                throws java.io.IOException {
+              if (hasName()) {
+                output.writeString(1, getName());
+              }
+              if (hasIcon()) {
+                output.writeBytes(2, getIcon());
+              }
+              getUnknownFields().writeTo(output);
+            }
+            
+            private int memoizedSerializedSize = -1;
+            public int getSerializedSize() {
+              int size = memoizedSerializedSize;
+              if (size != -1) return size;
+            
+              size = 0;
+              if (hasName()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(1, getName());
+              }
+              if (hasIcon()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeBytesSize(2, getIcon());
+              }
+              size += getUnknownFields().getSerializedSize();
+              memoizedSerializedSize = size;
+              return size;
+            }
+            
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(byte[] data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
+                byte[] data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseDelimitedFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseDelimitedFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            
+            public static Builder newBuilder() { return Builder.create(); }
+            public Builder newBuilderForType() { return newBuilder(); }
+            public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog prototype) {
+              return newBuilder().mergeFrom(prototype);
+            }
+            public Builder toBuilder() { return newBuilder(this); }
+            
+            public static final class Builder extends
+                com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog result;
+              
+              // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.newBuilder()
+              private Builder() {}
+              
+              private static Builder create() {
+                Builder builder = new Builder();
+                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog();
+                return builder;
+              }
+              
+              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog internalGetResult() {
+                return result;
+              }
+              
+              public Builder clear() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "Cannot call clear() after build().");
+                }
+                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog();
+                return this;
+              }
+              
+              public Builder clone() {
+                return create().mergeFrom(result);
+              }
+              
+              public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                  getDescriptorForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDescriptor();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog getDefaultInstanceForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance();
+              }
+              
+              public boolean isInitialized() {
+                return result.isInitialized();
+              }
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog build() {
+                if (result != null && !isInitialized()) {
+                  throw newUninitializedMessageException(result);
+                }
+                return buildPartial();
+              }
+              
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog buildParsed()
+                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+                if (!isInitialized()) {
+                  throw newUninitializedMessageException(
+                    result).asInvalidProtocolBufferException();
+                }
+                return buildPartial();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog buildPartial() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "build() has already been called on this Builder.");
+                }
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog returnMe = result;
+                result = null;
+                return returnMe;
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog) {
+                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog)other);
+                } else {
+                  super.mergeFrom(other);
+                  return this;
+                }
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog other) {
+                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance()) return this;
+                if (other.hasName()) {
+                  setName(other.getName());
+                }
+                if (other.hasIcon()) {
+                  setIcon(other.getIcon());
+                }
+                this.mergeUnknownFields(other.getUnknownFields());
+                return this;
+              }
+              
+              public Builder mergeFrom(
+                  com.google.gwt.dev.protobuf.CodedInputStream input,
+                  com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                  throws java.io.IOException {
+                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                  com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                    this.getUnknownFields());
+                while (true) {
+                  int tag = input.readTag();
+                  switch (tag) {
+                    case 0:
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    default: {
+                      if (!parseUnknownField(input, unknownFields,
+                                             extensionRegistry, tag)) {
+                        this.setUnknownFields(unknownFields.build());
+                        return this;
+                      }
+                      break;
+                    }
+                    case 10: {
+                      setName(input.readString());
+                      break;
+                    }
+                    case 18: {
+                      setIcon(input.readBytes());
+                      break;
+                    }
+                  }
+                }
+              }
+              
+              
+              // required string name = 1;
+              public boolean hasName() {
+                return result.hasName();
+              }
+              public java.lang.String getName() {
+                return result.getName();
+              }
+              public Builder setName(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasName = true;
+                result.name_ = value;
+                return this;
+              }
+              public Builder clearName() {
+                result.hasName = false;
+                result.name_ = getDefaultInstance().getName();
+                return this;
+              }
+              
+              // optional bytes icon = 2;
+              public boolean hasIcon() {
+                return result.hasIcon();
+              }
+              public com.google.gwt.dev.protobuf.ByteString getIcon() {
+                return result.getIcon();
+              }
+              public Builder setIcon(com.google.gwt.dev.protobuf.ByteString value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasIcon = true;
+                result.icon_ = value;
+                return this;
+              }
+              public Builder clearIcon() {
+                result.hasIcon = false;
+                result.icon_ = getDefaultInstance().getIcon();
+                return this;
+              }
+            }
+            
+            static {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+            }
+            
+            static {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+            }
+          }
+          
+          public static final class MainLog extends
+              com.google.gwt.dev.protobuf.GeneratedMessage {
+            // Use MainLog.newBuilder() to construct.
+            private MainLog() {}
+            
+            private static final MainLog defaultInstance = new MainLog();
+            public static MainLog getDefaultInstance() {
+              return defaultInstance;
+            }
+            
+            public MainLog getDefaultInstanceForType() {
+              return defaultInstance;
+            }
+            
+            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptor() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor;
+            }
+            
+            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+                internalGetFieldAccessorTable() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_fieldAccessorTable;
+            }
+            
+            public final boolean isInitialized() {
+              return true;
+            }
+            
+            public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                                throws java.io.IOException {
+              getUnknownFields().writeTo(output);
+            }
+            
+            private int memoizedSerializedSize = -1;
+            public int getSerializedSize() {
+              int size = memoizedSerializedSize;
+              if (size != -1) return size;
+            
+              size = 0;
+              size += getUnknownFields().getSerializedSize();
+              memoizedSerializedSize = size;
+              return size;
+            }
+            
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(byte[] data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
+                byte[] data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseDelimitedFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseDelimitedFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            
+            public static Builder newBuilder() { return Builder.create(); }
+            public Builder newBuilderForType() { return newBuilder(); }
+            public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog prototype) {
+              return newBuilder().mergeFrom(prototype);
+            }
+            public Builder toBuilder() { return newBuilder(this); }
+            
+            public static final class Builder extends
+                com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog result;
+              
+              // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.newBuilder()
+              private Builder() {}
+              
+              private static Builder create() {
+                Builder builder = new Builder();
+                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog();
+                return builder;
+              }
+              
+              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog internalGetResult() {
+                return result;
+              }
+              
+              public Builder clear() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "Cannot call clear() after build().");
+                }
+                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog();
+                return this;
+              }
+              
+              public Builder clone() {
+                return create().mergeFrom(result);
+              }
+              
+              public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                  getDescriptorForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDescriptor();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog getDefaultInstanceForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance();
+              }
+              
+              public boolean isInitialized() {
+                return result.isInitialized();
+              }
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog build() {
+                if (result != null && !isInitialized()) {
+                  throw newUninitializedMessageException(result);
+                }
+                return buildPartial();
+              }
+              
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog buildParsed()
+                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+                if (!isInitialized()) {
+                  throw newUninitializedMessageException(
+                    result).asInvalidProtocolBufferException();
+                }
+                return buildPartial();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog buildPartial() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "build() has already been called on this Builder.");
+                }
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog returnMe = result;
+                result = null;
+                return returnMe;
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog) {
+                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog)other);
+                } else {
+                  super.mergeFrom(other);
+                  return this;
+                }
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog other) {
+                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance()) return this;
+                this.mergeUnknownFields(other.getUnknownFields());
+                return this;
+              }
+              
+              public Builder mergeFrom(
+                  com.google.gwt.dev.protobuf.CodedInputStream input,
+                  com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                  throws java.io.IOException {
+                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                  com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                    this.getUnknownFields());
+                while (true) {
+                  int tag = input.readTag();
+                  switch (tag) {
+                    case 0:
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    default: {
+                      if (!parseUnknownField(input, unknownFields,
+                                             extensionRegistry, tag)) {
+                        this.setUnknownFields(unknownFields.build());
+                        return this;
+                      }
+                      break;
+                    }
+                  }
+                }
+              }
+              
+            }
+            
+            static {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+            }
+            
+            static {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+            }
+          }
+          
+          // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.LogType type = 1;
+          public static final int TYPE_FIELD_NUMBER = 1;
+          private boolean hasType;
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType type_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType.MAIN;
+          public boolean hasType() { return hasType; }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType getType() { return type_; }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ModuleLog moduleLog = 2;
+          public static final int MODULELOG_FIELD_NUMBER = 2;
+          private boolean hasModuleLog;
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog moduleLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance();
+          public boolean hasModuleLog() { return hasModuleLog; }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog getModuleLog() { return moduleLog_; }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ServerLog serverLog = 3;
+          public static final int SERVERLOG_FIELD_NUMBER = 3;
+          private boolean hasServerLog;
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog serverLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance();
+          public boolean hasServerLog() { return hasServerLog; }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog getServerLog() { return serverLog_; }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.MainLog mainLog = 4;
+          public static final int MAINLOG_FIELD_NUMBER = 4;
+          private boolean hasMainLog;
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog mainLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance();
+          public boolean hasMainLog() { return hasMainLog; }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog getMainLog() { return mainLog_; }
+          
+          public final boolean isInitialized() {
+            if (!hasType) return false;
+            if (hasModuleLog()) {
+              if (!getModuleLog().isInitialized()) return false;
+            }
+            if (hasServerLog()) {
+              if (!getServerLog().isInitialized()) return false;
+            }
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            if (hasType()) {
+              output.writeEnum(1, getType().getNumber());
+            }
+            if (hasModuleLog()) {
+              output.writeMessage(2, getModuleLog());
+            }
+            if (hasServerLog()) {
+              output.writeMessage(3, getServerLog());
+            }
+            if (hasMainLog()) {
+              output.writeMessage(4, getMainLog());
+            }
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            if (hasType()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeEnumSize(1, getType().getNumber());
+            }
+            if (hasModuleLog()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(2, getModuleLog());
+            }
+            if (hasServerLog()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(3, getServerLog());
+            }
+            if (hasMainLog()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(4, getMainLog());
+            }
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
+          }
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.newBuilder()
+            private Builder() {}
+            
             private static Builder create() {
               Builder builder = new Builder();
               builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog();
               return builder;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.newBuilder()
-            private Builder() {
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog internalGetResult() {
+              return result;
             }
-
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog build() {
               if (result != null && !isInitialized()) {
                 throw newUninitializedMessageException(result);
               }
               return buildPartial();
             }
-
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog buildPartial() {
               if (result == null) {
                 throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
+                  "build() has already been called on this Builder.");
               }
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog returnMe = result;
               result = null;
               return returnMe;
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
               }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog();
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance()) return this;
+              if (other.hasType()) {
+                setType(other.getType());
+              }
+              if (other.hasModuleLog()) {
+                mergeModuleLog(other.getModuleLog());
+              }
+              if (other.hasServerLog()) {
+                mergeServerLog(other.getServerLog());
+              }
+              if (other.hasMainLog()) {
+                mergeMainLog(other.getMainLog());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
               return this;
             }
-
-            public Builder clearMainLog() {
-              result.hasMainLog = false;
-              result.mainLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance();
-              return this;
-            }
-
-            public Builder clearModuleLog() {
-              result.hasModuleLog = false;
-              result.moduleLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance();
-              return this;
-            }
-
-            public Builder clearServerLog() {
-              result.hasServerLog = false;
-              result.serverLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance();
-              return this;
-            }
-
-            public Builder clearType() {
-              result.hasType = false;
-              result.type_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType.MAIN;
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDescriptor();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog getMainLog() {
-              return result.getMainLog();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog getModuleLog() {
-              return result.getModuleLog();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog getServerLog() {
-              return result.getServerLog();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType getType() {
-              return result.getType();
-            }
-
-            // optional
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.MainLog
-            // mainLog = 4;
-            public boolean hasMainLog() {
-              return result.hasMainLog();
-            }
-
-            // optional
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ModuleLog
-            // moduleLog = 2;
-            public boolean hasModuleLog() {
-              return result.hasModuleLog();
-            }
-
-            // optional
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ServerLog
-            // serverLog = 3;
-            public boolean hasServerLog() {
-              return result.hasServerLog();
-            }
-
-            // required
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.LogType
-            // type = 1;
-            public boolean hasType() {
-              return result.hasType();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
+            
             public Builder mergeFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
               while (true) {
                 int tag = input.readTag();
                 switch (tag) {
@@ -1873,7 +1923,7 @@
                     return this;
                   default: {
                     if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
+                                           extensionRegistry, tag)) {
                       this.setUnknownFields(unknownFields.build());
                       return this;
                     }
@@ -1919,128 +1969,16 @@
                 }
               }
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            
+            // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.LogType type = 1;
+            public boolean hasType() {
+              return result.hasType();
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance())
-                return this;
-              if (other.hasType()) {
-                setType(other.getType());
-              }
-              if (other.hasModuleLog()) {
-                mergeModuleLog(other.getModuleLog());
-              }
-              if (other.hasServerLog()) {
-                mergeServerLog(other.getServerLog());
-              }
-              if (other.hasMainLog()) {
-                mergeMainLog(other.getMainLog());
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType getType() {
+              return result.getType();
             }
-
-            public Builder mergeMainLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog value) {
-              if (result.hasMainLog()
-                  && result.mainLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance()) {
-                result.mainLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.newBuilder(
-                    result.mainLog_).mergeFrom(value).buildPartial();
-              } else {
-                result.mainLog_ = value;
-              }
-              result.hasMainLog = true;
-              return this;
-            }
-
-            public Builder mergeModuleLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog value) {
-              if (result.hasModuleLog()
-                  && result.moduleLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance()) {
-                result.moduleLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.newBuilder(
-                    result.moduleLog_).mergeFrom(value).buildPartial();
-              } else {
-                result.moduleLog_ = value;
-              }
-              result.hasModuleLog = true;
-              return this;
-            }
-
-            public Builder mergeServerLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog value) {
-              if (result.hasServerLog()
-                  && result.serverLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance()) {
-                result.serverLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.newBuilder(
-                    result.serverLog_).mergeFrom(value).buildPartial();
-              } else {
-                result.serverLog_ = value;
-              }
-              result.hasServerLog = true;
-              return this;
-            }
-
-            public Builder setMainLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.hasMainLog = true;
-              result.mainLog_ = value;
-              return this;
-            }
-
-            public Builder setMainLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.Builder builderForValue) {
-              result.hasMainLog = true;
-              result.mainLog_ = builderForValue.build();
-              return this;
-            }
-
-            public Builder setModuleLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.hasModuleLog = true;
-              result.moduleLog_ = value;
-              return this;
-            }
-
-            public Builder setModuleLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.Builder builderForValue) {
-              result.hasModuleLog = true;
-              result.moduleLog_ = builderForValue.build();
-              return this;
-            }
-
-            public Builder setServerLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.hasServerLog = true;
-              result.serverLog_ = value;
-              return this;
-            }
-
-            public Builder setServerLog(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.Builder builderForValue) {
-              result.hasServerLog = true;
-              result.serverLog_ = builderForValue.build();
-              return this;
-            }
-
-            public Builder setType(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType value) {
+            public Builder setType(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType value) {
               if (value == null) {
                 throw new NullPointerException();
               }
@@ -2048,151 +1986,390 @@
               result.type_ = value;
               return this;
             }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog internalGetResult() {
-              return result;
+            public Builder clearType() {
+              result.hasType = false;
+              result.type_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType.MAIN;
+              return this;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
+            
+            // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ModuleLog moduleLog = 2;
+            public boolean hasModuleLog() {
+              return result.hasModuleLog();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog getModuleLog() {
+              return result.getModuleLog();
+            }
+            public Builder setModuleLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog value) {
+              if (value == null) {
+                throw new NullPointerException();
               }
-              return buildPartial();
+              result.hasModuleLog = true;
+              result.moduleLog_ = value;
+              return this;
+            }
+            public Builder setModuleLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.Builder builderForValue) {
+              result.hasModuleLog = true;
+              result.moduleLog_ = builderForValue.build();
+              return this;
+            }
+            public Builder mergeModuleLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog value) {
+              if (result.hasModuleLog() &&
+                  result.moduleLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance()) {
+                result.moduleLog_ =
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.newBuilder(result.moduleLog_).mergeFrom(value).buildPartial();
+              } else {
+                result.moduleLog_ = value;
+              }
+              result.hasModuleLog = true;
+              return this;
+            }
+            public Builder clearModuleLog() {
+              result.hasModuleLog = false;
+              result.moduleLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance();
+              return this;
+            }
+            
+            // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ServerLog serverLog = 3;
+            public boolean hasServerLog() {
+              return result.hasServerLog();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog getServerLog() {
+              return result.getServerLog();
+            }
+            public Builder setServerLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog value) {
+              if (value == null) {
+                throw new NullPointerException();
+              }
+              result.hasServerLog = true;
+              result.serverLog_ = value;
+              return this;
+            }
+            public Builder setServerLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.Builder builderForValue) {
+              result.hasServerLog = true;
+              result.serverLog_ = builderForValue.build();
+              return this;
+            }
+            public Builder mergeServerLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog value) {
+              if (result.hasServerLog() &&
+                  result.serverLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance()) {
+                result.serverLog_ =
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.newBuilder(result.serverLog_).mergeFrom(value).buildPartial();
+              } else {
+                result.serverLog_ = value;
+              }
+              result.hasServerLog = true;
+              return this;
+            }
+            public Builder clearServerLog() {
+              result.hasServerLog = false;
+              result.serverLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance();
+              return this;
+            }
+            
+            // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.MainLog mainLog = 4;
+            public boolean hasMainLog() {
+              return result.hasMainLog();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog getMainLog() {
+              return result.getMainLog();
+            }
+            public Builder setMainLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog value) {
+              if (value == null) {
+                throw new NullPointerException();
+              }
+              result.hasMainLog = true;
+              result.mainLog_ = value;
+              return this;
+            }
+            public Builder setMainLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.Builder builderForValue) {
+              result.hasMainLog = true;
+              result.mainLog_ = builderForValue.build();
+              return this;
+            }
+            public Builder mergeMainLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog value) {
+              if (result.hasMainLog() &&
+                  result.mainLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance()) {
+                result.mainLog_ =
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.newBuilder(result.mainLog_).mergeFrom(value).buildPartial();
+              } else {
+                result.mainLog_ = value;
+              }
+              result.hasMainLog = true;
+              return this;
+            }
+            public Builder clearMainLog() {
+              result.hasMainLog = false;
+              result.mainLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance();
+              return this;
             }
           }
-
-          public enum LogType implements
-              com.google.gwt.dev.protobuf.ProtocolMessageEnum {
-            MAIN(0, 0), MODULE(1, 1), WEB_SERVER(2, 2), ;
-
-            private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<LogType> internalValueMap = new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<LogType>() {
-              public LogType findValueByNumber(int number) {
-                return LogType.valueOf(number);
-              }
-            };
-
-            private static final LogType[] VALUES = {MAIN, MODULE, WEB_SERVER,};
-
-            public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptor() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDescriptor().getEnumTypes().get(
-                  0);
-            }
-
-            public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<LogType> internalGetValueMap() {
-              return internalValueMap;
-            }
-
-            public static LogType valueOf(
-                com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
-              if (desc.getType() != getDescriptor()) {
-                throw new java.lang.IllegalArgumentException(
-                    "EnumValueDescriptor is not for this type.");
-              }
-              return VALUES[desc.getIndex()];
-            }
-
-            public static LogType valueOf(int value) {
-              switch (value) {
-                case 0:
-                  return MAIN;
-                case 1:
-                  return MODULE;
-                case 2:
-                  return WEB_SERVER;
-                default:
-                  return null;
-              }
-            }
-
-            private final int index;
-
-            private final int value;
-            static {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-            }
-
-            private LogType(int index, int value) {
-              this.index = index;
-              this.value = value;
-            }
-
-            public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptorForType() {
-              return getDescriptor();
-            }
-
-            public final int getNumber() {
-              return value;
-            }
-
-            public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() {
-              return getDescriptor().getValues().get(index);
-            }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
-          public static final class MainLog extends
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+          }
+        }
+        
+        public static final class LogData extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use LogData.newBuilder() to construct.
+          private LogData() {}
+          
+          private static final LogData defaultInstance = new LogData();
+          public static LogData getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public LogData getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_fieldAccessorTable;
+          }
+          
+          public static final class HelpInfo extends
               com.google.gwt.dev.protobuf.GeneratedMessage {
+            // Use HelpInfo.newBuilder() to construct.
+            private HelpInfo() {}
+            
+            private static final HelpInfo defaultInstance = new HelpInfo();
+            public static HelpInfo getDefaultInstance() {
+              return defaultInstance;
+            }
+            
+            public HelpInfo getDefaultInstanceForType() {
+              return defaultInstance;
+            }
+            
+            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptor() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor;
+            }
+            
+            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+                internalGetFieldAccessorTable() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_fieldAccessorTable;
+            }
+            
+            // optional string url = 1;
+            public static final int URL_FIELD_NUMBER = 1;
+            private boolean hasUrl;
+            private java.lang.String url_ = "";
+            public boolean hasUrl() { return hasUrl; }
+            public java.lang.String getUrl() { return url_; }
+            
+            // optional string text = 2;
+            public static final int TEXT_FIELD_NUMBER = 2;
+            private boolean hasText;
+            private java.lang.String text_ = "";
+            public boolean hasText() { return hasText; }
+            public java.lang.String getText() { return text_; }
+            
+            public final boolean isInitialized() {
+              return true;
+            }
+            
+            public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                                throws java.io.IOException {
+              if (hasUrl()) {
+                output.writeString(1, getUrl());
+              }
+              if (hasText()) {
+                output.writeString(2, getText());
+              }
+              getUnknownFields().writeTo(output);
+            }
+            
+            private int memoizedSerializedSize = -1;
+            public int getSerializedSize() {
+              int size = memoizedSerializedSize;
+              if (size != -1) return size;
+            
+              size = 0;
+              if (hasUrl()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(1, getUrl());
+              }
+              if (hasText()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeStringSize(2, getText());
+              }
+              size += getUnknownFields().getSerializedSize();
+              memoizedSerializedSize = size;
+              return size;
+            }
+            
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(byte[] data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
+                byte[] data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseDelimitedFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseDelimitedFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
+            }
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
+            }
+            
+            public static Builder newBuilder() { return Builder.create(); }
+            public Builder newBuilderForType() { return newBuilder(); }
+            public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo prototype) {
+              return newBuilder().mergeFrom(prototype);
+            }
+            public Builder toBuilder() { return newBuilder(this); }
+            
             public static final class Builder extends
                 com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo result;
+              
+              // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.newBuilder()
+              private Builder() {}
+              
               private static Builder create() {
                 Builder builder = new Builder();
-                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog();
+                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo();
                 return builder;
               }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog result;
-
-              // Construct using
-              // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.newBuilder()
-              private Builder() {
+              
+              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo internalGetResult() {
+                return result;
               }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog build() {
+              
+              public Builder clear() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "Cannot call clear() after build().");
+                }
+                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo();
+                return this;
+              }
+              
+              public Builder clone() {
+                return create().mergeFrom(result);
+              }
+              
+              public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                  getDescriptorForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDescriptor();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo getDefaultInstanceForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance();
+              }
+              
+              public boolean isInitialized() {
+                return result.isInitialized();
+              }
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo build() {
                 if (result != null && !isInitialized()) {
                   throw newUninitializedMessageException(result);
                 }
                 return buildPartial();
               }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog buildPartial() {
+              
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo buildParsed()
+                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+                if (!isInitialized()) {
+                  throw newUninitializedMessageException(
+                    result).asInvalidProtocolBufferException();
+                }
+                return buildPartial();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo buildPartial() {
                 if (result == null) {
                   throw new IllegalStateException(
-                      "build() has already been called on this Builder.");
+                    "build() has already been called on this Builder.");
                 }
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog returnMe = result;
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo returnMe = result;
                 result = null;
                 return returnMe;
               }
-
-              public Builder clear() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "Cannot call clear() after build().");
+              
+              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo) {
+                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo)other);
+                } else {
+                  super.mergeFrom(other);
+                  return this;
                 }
-                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog();
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo other) {
+                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance()) return this;
+                if (other.hasUrl()) {
+                  setUrl(other.getUrl());
+                }
+                if (other.hasText()) {
+                  setText(other.getText());
+                }
+                this.mergeUnknownFields(other.getUnknownFields());
                 return this;
               }
-
-              public Builder clone() {
-                return create().mergeFrom(result);
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog getDefaultInstanceForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance();
-              }
-
-              public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDescriptor();
-              }
-
-              public boolean isInitialized() {
-                return result.isInitialized();
-              }
-
+              
               public Builder mergeFrom(
                   com.google.gwt.dev.protobuf.CodedInputStream input,
                   com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                   throws java.io.IOException {
-                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                  com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                    this.getUnknownFields());
                 while (true) {
                   int tag = input.readTag();
                   switch (tag) {
@@ -2201,1480 +2378,321 @@
                       return this;
                     default: {
                       if (!parseUnknownField(input, unknownFields,
-                          extensionRegistry, tag)) {
+                                             extensionRegistry, tag)) {
                         this.setUnknownFields(unknownFields.build());
                         return this;
                       }
                       break;
                     }
+                    case 10: {
+                      setUrl(input.readString());
+                      break;
+                    }
+                    case 18: {
+                      setText(input.readString());
+                      break;
+                    }
                   }
                 }
               }
-
-              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog) {
-                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog) other);
-                } else {
-                  super.mergeFrom(other);
-                  return this;
-                }
+              
+              
+              // optional string url = 1;
+              public boolean hasUrl() {
+                return result.hasUrl();
               }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog other) {
-                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance())
-                  return this;
-                this.mergeUnknownFields(other.getUnknownFields());
+              public java.lang.String getUrl() {
+                return result.getUrl();
+              }
+              public Builder setUrl(java.lang.String value) {
+                if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasUrl = true;
+                result.url_ = value;
                 return this;
               }
-
-              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog internalGetResult() {
-                return result;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog buildParsed()
-                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-                if (!isInitialized()) {
-                  throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-                }
-                return buildPartial();
-              }
-
-            }
-
-            private static final MainLog defaultInstance = new MainLog();
-            static {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-            }
-
-            static {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-            }
-
-            public static MainLog getDefaultInstance() {
-              return defaultInstance;
-            }
-
-            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor;
-            }
-
-            public static Builder newBuilder() {
-              return Builder.create();
-            }
-
-            public static Builder newBuilder(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog prototype) {
-              return newBuilder().mergeFrom(prototype);
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseDelimitedFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseDelimitedFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                byte[] data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                byte[] data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog parseFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            private int memoizedSerializedSize = -1;
-
-            // Use MainLog.newBuilder() to construct.
-            private MainLog() {
-            }
-
-            public MainLog getDefaultInstanceForType() {
-              return defaultInstance;
-            }
-
-            public int getSerializedSize() {
-              int size = memoizedSerializedSize;
-              if (size != -1)
-                return size;
-
-              size = 0;
-              size += getUnknownFields().getSerializedSize();
-              memoizedSerializedSize = size;
-              return size;
-            }
-
-            public final boolean isInitialized() {
-              return true;
-            }
-
-            public Builder newBuilderForType() {
-              return newBuilder();
-            }
-
-            public Builder toBuilder() {
-              return newBuilder(this);
-            }
-
-            public void writeTo(
-                com.google.gwt.dev.protobuf.CodedOutputStream output)
-                throws java.io.IOException {
-              getUnknownFields().writeTo(output);
-            }
-
-            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_fieldAccessorTable;
-            }
-          }
-
-          public static final class ModuleLog extends
-              com.google.gwt.dev.protobuf.GeneratedMessage {
-            public static final class Builder extends
-                com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-              private static Builder create() {
-                Builder builder = new Builder();
-                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog();
-                return builder;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog result;
-
-              // Construct using
-              // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.newBuilder()
-              private Builder() {
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog build() {
-                if (result != null && !isInitialized()) {
-                  throw newUninitializedMessageException(result);
-                }
-                return buildPartial();
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog buildPartial() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "build() has already been called on this Builder.");
-                }
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog returnMe = result;
-                result = null;
-                return returnMe;
-              }
-
-              public Builder clear() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "Cannot call clear() after build().");
-                }
-                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog();
-                return this;
-              }
-
-              public Builder clearIcon() {
-                result.hasIcon = false;
-                result.icon_ = getDefaultInstance().getIcon();
-                return this;
-              }
-
-              public Builder clearName() {
-                result.hasName = false;
-                result.name_ = getDefaultInstance().getName();
-                return this;
-              }
-
-              public Builder clearRemoteHost() {
-                result.hasRemoteHost = false;
-                result.remoteHost_ = getDefaultInstance().getRemoteHost();
-                return this;
-              }
-
-              public Builder clearSessionKey() {
-                result.hasSessionKey = false;
-                result.sessionKey_ = getDefaultInstance().getSessionKey();
-                return this;
-              }
-
-              public Builder clearTabKey() {
-                result.hasTabKey = false;
-                result.tabKey_ = getDefaultInstance().getTabKey();
-                return this;
-              }
-
               public Builder clearUrl() {
                 result.hasUrl = false;
                 result.url_ = getDefaultInstance().getUrl();
                 return this;
               }
-
-              public Builder clearUserAgent() {
-                result.hasUserAgent = false;
-                result.userAgent_ = getDefaultInstance().getUserAgent();
-                return this;
+              
+              // optional string text = 2;
+              public boolean hasText() {
+                return result.hasText();
               }
-
-              public Builder clone() {
-                return create().mergeFrom(result);
+              public java.lang.String getText() {
+                return result.getText();
               }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog getDefaultInstanceForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance();
-              }
-
-              public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDescriptor();
-              }
-
-              public com.google.gwt.dev.protobuf.ByteString getIcon() {
-                return result.getIcon();
-              }
-
-              public java.lang.String getName() {
-                return result.getName();
-              }
-
-              public java.lang.String getRemoteHost() {
-                return result.getRemoteHost();
-              }
-
-              public java.lang.String getSessionKey() {
-                return result.getSessionKey();
-              }
-
-              public java.lang.String getTabKey() {
-                return result.getTabKey();
-              }
-
-              public java.lang.String getUrl() {
-                return result.getUrl();
-              }
-
-              public java.lang.String getUserAgent() {
-                return result.getUserAgent();
-              }
-
-              // optional bytes icon = 2;
-              public boolean hasIcon() {
-                return result.hasIcon();
-              }
-
-              // required string name = 1;
-              public boolean hasName() {
-                return result.hasName();
-              }
-
-              // optional string remoteHost = 7;
-              public boolean hasRemoteHost() {
-                return result.hasRemoteHost();
-              }
-
-              // optional string sessionKey = 3;
-              public boolean hasSessionKey() {
-                return result.hasSessionKey();
-              }
-
-              // optional string tabKey = 6;
-              public boolean hasTabKey() {
-                return result.hasTabKey();
-              }
-
-              // optional string url = 5;
-              public boolean hasUrl() {
-                return result.hasUrl();
-              }
-
-              // optional string userAgent = 4;
-              public boolean hasUserAgent() {
-                return result.hasUserAgent();
-              }
-
-              public boolean isInitialized() {
-                return result.isInitialized();
-              }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.protobuf.CodedInputStream input,
-                  com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                  throws java.io.IOException {
-                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-                while (true) {
-                  int tag = input.readTag();
-                  switch (tag) {
-                    case 0:
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    default: {
-                      if (!parseUnknownField(input, unknownFields,
-                          extensionRegistry, tag)) {
-                        this.setUnknownFields(unknownFields.build());
-                        return this;
-                      }
-                      break;
-                    }
-                    case 10: {
-                      setName(input.readString());
-                      break;
-                    }
-                    case 18: {
-                      setIcon(input.readBytes());
-                      break;
-                    }
-                    case 26: {
-                      setSessionKey(input.readString());
-                      break;
-                    }
-                    case 34: {
-                      setUserAgent(input.readString());
-                      break;
-                    }
-                    case 42: {
-                      setUrl(input.readString());
-                      break;
-                    }
-                    case 50: {
-                      setTabKey(input.readString());
-                      break;
-                    }
-                    case 58: {
-                      setRemoteHost(input.readString());
-                      break;
-                    }
-                  }
-                }
-              }
-
-              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog) {
-                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog) other);
-                } else {
-                  super.mergeFrom(other);
-                  return this;
-                }
-              }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog other) {
-                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance())
-                  return this;
-                if (other.hasName()) {
-                  setName(other.getName());
-                }
-                if (other.hasIcon()) {
-                  setIcon(other.getIcon());
-                }
-                if (other.hasSessionKey()) {
-                  setSessionKey(other.getSessionKey());
-                }
-                if (other.hasUserAgent()) {
-                  setUserAgent(other.getUserAgent());
-                }
-                if (other.hasUrl()) {
-                  setUrl(other.getUrl());
-                }
-                if (other.hasTabKey()) {
-                  setTabKey(other.getTabKey());
-                }
-                if (other.hasRemoteHost()) {
-                  setRemoteHost(other.getRemoteHost());
-                }
-                this.mergeUnknownFields(other.getUnknownFields());
-                return this;
-              }
-
-              public Builder setIcon(
-                  com.google.gwt.dev.protobuf.ByteString value) {
+              public Builder setText(java.lang.String value) {
                 if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasIcon = true;
-                result.icon_ = value;
+    throw new NullPointerException();
+  }
+  result.hasText = true;
+                result.text_ = value;
                 return this;
               }
-
-              public Builder setName(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasName = true;
-                result.name_ = value;
+              public Builder clearText() {
+                result.hasText = false;
+                result.text_ = getDefaultInstance().getText();
                 return this;
               }
-
-              public Builder setRemoteHost(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasRemoteHost = true;
-                result.remoteHost_ = value;
-                return this;
-              }
-
-              public Builder setSessionKey(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasSessionKey = true;
-                result.sessionKey_ = value;
-                return this;
-              }
-
-              public Builder setTabKey(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasTabKey = true;
-                result.tabKey_ = value;
-                return this;
-              }
-
-              public Builder setUrl(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasUrl = true;
-                result.url_ = value;
-                return this;
-              }
-
-              public Builder setUserAgent(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasUserAgent = true;
-                result.userAgent_ = value;
-                return this;
-              }
-
-              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog internalGetResult() {
-                return result;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog buildParsed()
-                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-                if (!isInitialized()) {
-                  throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-                }
-                return buildPartial();
-              }
             }
-
-            private static final ModuleLog defaultInstance = new ModuleLog();
-            // required string name = 1;
-            public static final int NAME_FIELD_NUMBER = 1;
-
-            // optional string sessionKey = 3;
-            public static final int SESSIONKEY_FIELD_NUMBER = 3;
-
-            // optional string tabKey = 6;
-            public static final int TABKEY_FIELD_NUMBER = 6;
-
+            
             static {
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
             }
-
+            
             static {
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
             }
-
-            public static ModuleLog getDefaultInstance() {
-              return defaultInstance;
-            }
-
-            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor;
-            }
-
-            public static Builder newBuilder() {
-              return Builder.create();
-            }
-
-            public static Builder newBuilder(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog prototype) {
-              return newBuilder().mergeFrom(prototype);
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseDelimitedFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseDelimitedFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                byte[] data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                byte[] data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog parseFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            private boolean hasName;
-            private java.lang.String name_ = "";
-            // optional bytes icon = 2;
-            public static final int ICON_FIELD_NUMBER = 2;
-            private boolean hasIcon;
-            private com.google.gwt.dev.protobuf.ByteString icon_ = com.google.gwt.dev.protobuf.ByteString.EMPTY;
-
-            private boolean hasSessionKey;
-            private java.lang.String sessionKey_ = "";
-            // optional string userAgent = 4;
-            public static final int USERAGENT_FIELD_NUMBER = 4;
-            private boolean hasUserAgent;
-            private java.lang.String userAgent_ = "";
-
-            // optional string url = 5;
-            public static final int URL_FIELD_NUMBER = 5;
-            private boolean hasUrl;
-            private java.lang.String url_ = "";
-            private boolean hasTabKey;
-            private java.lang.String tabKey_ = "";
-
-            // optional string remoteHost = 7;
-            public static final int REMOTEHOST_FIELD_NUMBER = 7;
-            private boolean hasRemoteHost;
-            private java.lang.String remoteHost_ = "";
-            private int memoizedSerializedSize = -1;
-
-            // Use ModuleLog.newBuilder() to construct.
-            private ModuleLog() {
-            }
-
-            public ModuleLog getDefaultInstanceForType() {
-              return defaultInstance;
-            }
-
-            public com.google.gwt.dev.protobuf.ByteString getIcon() {
-              return icon_;
-            }
-
-            public java.lang.String getName() {
-              return name_;
-            }
-
-            public java.lang.String getRemoteHost() {
-              return remoteHost_;
-            }
-
-            public int getSerializedSize() {
-              int size = memoizedSerializedSize;
-              if (size != -1)
-                return size;
-
-              size = 0;
-              if (hasName()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    1, getName());
-              }
-              if (hasIcon()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeBytesSize(
-                    2, getIcon());
-              }
-              if (hasSessionKey()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    3, getSessionKey());
-              }
-              if (hasUserAgent()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    4, getUserAgent());
-              }
-              if (hasUrl()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    5, getUrl());
-              }
-              if (hasTabKey()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    6, getTabKey());
-              }
-              if (hasRemoteHost()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    7, getRemoteHost());
-              }
-              size += getUnknownFields().getSerializedSize();
-              memoizedSerializedSize = size;
-              return size;
-            }
-
-            public java.lang.String getSessionKey() {
-              return sessionKey_;
-            }
-
-            public java.lang.String getTabKey() {
-              return tabKey_;
-            }
-
-            public java.lang.String getUrl() {
-              return url_;
-            }
-
-            public java.lang.String getUserAgent() {
-              return userAgent_;
-            }
-
-            public boolean hasIcon() {
-              return hasIcon;
-            }
-
-            public boolean hasName() {
-              return hasName;
-            }
-
-            public boolean hasRemoteHost() {
-              return hasRemoteHost;
-            }
-
-            public boolean hasSessionKey() {
-              return hasSessionKey;
-            }
-
-            public boolean hasTabKey() {
-              return hasTabKey;
-            }
-
-            public boolean hasUrl() {
-              return hasUrl;
-            }
-
-            public boolean hasUserAgent() {
-              return hasUserAgent;
-            }
-
-            public final boolean isInitialized() {
-              if (!hasName)
-                return false;
-              return true;
-            }
-
-            public Builder newBuilderForType() {
-              return newBuilder();
-            }
-
-            public Builder toBuilder() {
-              return newBuilder(this);
-            }
-
-            public void writeTo(
-                com.google.gwt.dev.protobuf.CodedOutputStream output)
-                throws java.io.IOException {
-              if (hasName()) {
-                output.writeString(1, getName());
-              }
-              if (hasIcon()) {
-                output.writeBytes(2, getIcon());
-              }
-              if (hasSessionKey()) {
-                output.writeString(3, getSessionKey());
-              }
-              if (hasUserAgent()) {
-                output.writeString(4, getUserAgent());
-              }
-              if (hasUrl()) {
-                output.writeString(5, getUrl());
-              }
-              if (hasTabKey()) {
-                output.writeString(6, getTabKey());
-              }
-              if (hasRemoteHost()) {
-                output.writeString(7, getRemoteHost());
-              }
-              getUnknownFields().writeTo(output);
-            }
-
-            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_fieldAccessorTable;
-            }
           }
-
-          public static final class ServerLog extends
-              com.google.gwt.dev.protobuf.GeneratedMessage {
-            public static final class Builder extends
-                com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-              private static Builder create() {
-                Builder builder = new Builder();
-                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog();
-                return builder;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog result;
-
-              // Construct using
-              // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.newBuilder()
-              private Builder() {
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog build() {
-                if (result != null && !isInitialized()) {
-                  throw newUninitializedMessageException(result);
-                }
-                return buildPartial();
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog buildPartial() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "build() has already been called on this Builder.");
-                }
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog returnMe = result;
-                result = null;
-                return returnMe;
-              }
-
-              public Builder clear() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "Cannot call clear() after build().");
-                }
-                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog();
-                return this;
-              }
-
-              public Builder clearIcon() {
-                result.hasIcon = false;
-                result.icon_ = getDefaultInstance().getIcon();
-                return this;
-              }
-
-              public Builder clearName() {
-                result.hasName = false;
-                result.name_ = getDefaultInstance().getName();
-                return this;
-              }
-
-              public Builder clone() {
-                return create().mergeFrom(result);
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog getDefaultInstanceForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance();
-              }
-
-              public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDescriptor();
-              }
-
-              public com.google.gwt.dev.protobuf.ByteString getIcon() {
-                return result.getIcon();
-              }
-
-              public java.lang.String getName() {
-                return result.getName();
-              }
-
-              // optional bytes icon = 2;
-              public boolean hasIcon() {
-                return result.hasIcon();
-              }
-
-              // required string name = 1;
-              public boolean hasName() {
-                return result.hasName();
-              }
-
-              public boolean isInitialized() {
-                return result.isInitialized();
-              }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.protobuf.CodedInputStream input,
-                  com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                  throws java.io.IOException {
-                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-                while (true) {
-                  int tag = input.readTag();
-                  switch (tag) {
-                    case 0:
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    default: {
-                      if (!parseUnknownField(input, unknownFields,
-                          extensionRegistry, tag)) {
-                        this.setUnknownFields(unknownFields.build());
-                        return this;
-                      }
-                      break;
-                    }
-                    case 10: {
-                      setName(input.readString());
-                      break;
-                    }
-                    case 18: {
-                      setIcon(input.readBytes());
-                      break;
-                    }
-                  }
-                }
-              }
-
-              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog) {
-                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog) other);
-                } else {
-                  super.mergeFrom(other);
-                  return this;
-                }
-              }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog other) {
-                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance())
-                  return this;
-                if (other.hasName()) {
-                  setName(other.getName());
-                }
-                if (other.hasIcon()) {
-                  setIcon(other.getIcon());
-                }
-                this.mergeUnknownFields(other.getUnknownFields());
-                return this;
-              }
-
-              public Builder setIcon(
-                  com.google.gwt.dev.protobuf.ByteString value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasIcon = true;
-                result.icon_ = value;
-                return this;
-              }
-
-              public Builder setName(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasName = true;
-                result.name_ = value;
-                return this;
-              }
-
-              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog internalGetResult() {
-                return result;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog buildParsed()
-                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-                if (!isInitialized()) {
-                  throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-                }
-                return buildPartial();
-              }
-            }
-
-            private static final ServerLog defaultInstance = new ServerLog();
-            // required string name = 1;
-            public static final int NAME_FIELD_NUMBER = 1;
-
-            // optional bytes icon = 2;
-            public static final int ICON_FIELD_NUMBER = 2;
-
-            static {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-            }
-
-            static {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-            }
-
-            public static ServerLog getDefaultInstance() {
-              return defaultInstance;
-            }
-
-            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor;
-            }
-
-            public static Builder newBuilder() {
-              return Builder.create();
-            }
-
-            public static Builder newBuilder(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog prototype) {
-              return newBuilder().mergeFrom(prototype);
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseDelimitedFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseDelimitedFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                byte[] data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                byte[] data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog parseFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            private boolean hasName;
-            private java.lang.String name_ = "";
-            private boolean hasIcon;
-            private com.google.gwt.dev.protobuf.ByteString icon_ = com.google.gwt.dev.protobuf.ByteString.EMPTY;
-            private int memoizedSerializedSize = -1;
-
-            // Use ServerLog.newBuilder() to construct.
-            private ServerLog() {
-            }
-
-            public ServerLog getDefaultInstanceForType() {
-              return defaultInstance;
-            }
-
-            public com.google.gwt.dev.protobuf.ByteString getIcon() {
-              return icon_;
-            }
-
-            public java.lang.String getName() {
-              return name_;
-            }
-
-            public int getSerializedSize() {
-              int size = memoizedSerializedSize;
-              if (size != -1)
-                return size;
-
-              size = 0;
-              if (hasName()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    1, getName());
-              }
-              if (hasIcon()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeBytesSize(
-                    2, getIcon());
-              }
-              size += getUnknownFields().getSerializedSize();
-              memoizedSerializedSize = size;
-              return size;
-            }
-
-            public boolean hasIcon() {
-              return hasIcon;
-            }
-
-            public boolean hasName() {
-              return hasName;
-            }
-
-            public final boolean isInitialized() {
-              if (!hasName)
-                return false;
-              return true;
-            }
-
-            public Builder newBuilderForType() {
-              return newBuilder();
-            }
-
-            public Builder toBuilder() {
-              return newBuilder(this);
-            }
-
-            public void writeTo(
-                com.google.gwt.dev.protobuf.CodedOutputStream output)
-                throws java.io.IOException {
-              if (hasName()) {
-                output.writeString(1, getName());
-              }
-              if (hasIcon()) {
-                output.writeBytes(2, getIcon());
-              }
-              getUnknownFields().writeTo(output);
-            }
-
-            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_fieldAccessorTable;
-            }
+          
+          // required string summary = 1;
+          public static final int SUMMARY_FIELD_NUMBER = 1;
+          private boolean hasSummary;
+          private java.lang.String summary_ = "";
+          public boolean hasSummary() { return hasSummary; }
+          public java.lang.String getSummary() { return summary_; }
+          
+          // optional string level = 2;
+          public static final int LEVEL_FIELD_NUMBER = 2;
+          private boolean hasLevel;
+          private java.lang.String level_ = "";
+          public boolean hasLevel() { return hasLevel; }
+          public java.lang.String getLevel() { return level_; }
+          
+          // optional string details = 3;
+          public static final int DETAILS_FIELD_NUMBER = 3;
+          private boolean hasDetails;
+          private java.lang.String details_ = "";
+          public boolean hasDetails() { return hasDetails; }
+          public java.lang.String getDetails() { return details_; }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData.HelpInfo helpInfo = 4;
+          public static final int HELPINFO_FIELD_NUMBER = 4;
+          private boolean hasHelpInfo;
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo helpInfo_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance();
+          public boolean hasHelpInfo() { return hasHelpInfo; }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo getHelpInfo() { return helpInfo_; }
+          
+          public final boolean isInitialized() {
+            if (!hasSummary) return false;
+            return true;
           }
-
-          private static final AddLog defaultInstance = new AddLog();
-
-          // required
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.LogType
-          // type = 1;
-          public static final int TYPE_FIELD_NUMBER = 1;
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.MainLog
-          // mainLog = 4;
-          public static final int MAINLOG_FIELD_NUMBER = 4;
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            if (hasSummary()) {
+              output.writeString(1, getSummary());
+            }
+            if (hasLevel()) {
+              output.writeString(2, getLevel());
+            }
+            if (hasDetails()) {
+              output.writeString(3, getDetails());
+            }
+            if (hasHelpInfo()) {
+              output.writeMessage(4, getHelpInfo());
+            }
+            getUnknownFields().writeTo(output);
           }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static AddLog getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private boolean hasType;
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType type_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType.MAIN;
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ModuleLog
-          // moduleLog = 2;
-          public static final int MODULELOG_FIELD_NUMBER = 2;
-          private boolean hasModuleLog;
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog moduleLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.getDefaultInstance();
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog.ServerLog
-          // serverLog = 3;
-          public static final int SERVERLOG_FIELD_NUMBER = 3;
-
-          private boolean hasServerLog;
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog serverLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.getDefaultInstance();
-
-          private boolean hasMainLog;
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog mainLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.getDefaultInstance();
-
+          
           private int memoizedSerializedSize = -1;
-
-          // Use AddLog.newBuilder() to construct.
-          private AddLog() {
-          }
-
-          public AddLog getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog getMainLog() {
-            return mainLog_;
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog getModuleLog() {
-            return moduleLog_;
-          }
-
           public int getSerializedSize() {
             int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
+            if (size != -1) return size;
+          
             size = 0;
-            if (hasType()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-                  1, getType().getNumber());
+            if (hasSummary()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeStringSize(1, getSummary());
             }
-            if (hasModuleLog()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  2, getModuleLog());
+            if (hasLevel()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeStringSize(2, getLevel());
             }
-            if (hasServerLog()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  3, getServerLog());
+            if (hasDetails()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeStringSize(3, getDetails());
             }
-            if (hasMainLog()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  4, getMainLog());
+            if (hasHelpInfo()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(4, getHelpInfo());
             }
             size += getUnknownFields().getSerializedSize();
             memoizedSerializedSize = size;
             return size;
           }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog getServerLog() {
-            return serverLog_;
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.LogType getType() {
-            return type_;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-
-          public boolean hasMainLog() {
-            return hasMainLog;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public boolean hasModuleLog() {
-            return hasModuleLog;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-
-          public boolean hasServerLog() {
-            return hasServerLog;
-          }
-
-          public boolean hasType() {
-            return hasType;
-          }
-
-          public final boolean isInitialized() {
-            if (!hasType)
-              return false;
-            if (hasModuleLog()) {
-              if (!getModuleLog().isInitialized())
-                return false;
-            }
-            if (hasServerLog()) {
-              if (!getServerLog().isInitialized())
-                return false;
-            }
-            return true;
-          }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(java.io.InputStream input)
               throws java.io.IOException {
-            if (hasType()) {
-              output.writeEnum(1, getType().getNumber());
-            }
-            if (hasModuleLog()) {
-              output.writeMessage(2, getModuleLog());
-            }
-            if (hasServerLog()) {
-              output.writeMessage(3, getServerLog());
-            }
-            if (hasMainLog()) {
-              output.writeMessage(4, getMainLog());
-            }
-            getUnknownFields().writeTo(output);
+            return newBuilder().mergeFrom(input).buildParsed();
           }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_fieldAccessorTable;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
           }
-        }
-
-        public static final class AddLogBranch extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
           public static final class Builder extends
               com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.newBuilder()
+            private Builder() {}
+            
             private static Builder create() {
               Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData();
               return builder;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.newBuilder()
-            private Builder() {
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData internalGetResult() {
+              return result;
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch build() {
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData build() {
               if (result != null && !isInitialized()) {
                 throw newUninitializedMessageException(result);
               }
               return buildPartial();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch buildPartial() {
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData buildPartial() {
               if (result == null) {
                 throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
+                  "build() has already been called on this Builder.");
               }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch returnMe = result;
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData returnMe = result;
               result = null;
               return returnMe;
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
               }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch();
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance()) return this;
+              if (other.hasSummary()) {
+                setSummary(other.getSummary());
+              }
+              if (other.hasLevel()) {
+                setLevel(other.getLevel());
+              }
+              if (other.hasDetails()) {
+                setDetails(other.getDetails());
+              }
+              if (other.hasHelpInfo()) {
+                mergeHelpInfo(other.getHelpInfo());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
               return this;
             }
-
-            public Builder clearIndexInParent() {
-              result.hasIndexInParent = false;
-              result.indexInParent_ = 0;
-              return this;
-            }
-
-            public Builder clearLogData() {
-              result.hasLogData = false;
-              result.logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
-              return this;
-            }
-
-            public Builder clearParentLogHandle() {
-              result.hasParentLogHandle = false;
-              result.parentLogHandle_ = 0;
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDescriptor();
-            }
-
-            public int getIndexInParent() {
-              return result.getIndexInParent();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() {
-              return result.getLogData();
-            }
-
-            public int getParentLogHandle() {
-              return result.getParentLogHandle();
-            }
-
-            // required uint32 indexInParent = 2;
-            public boolean hasIndexInParent() {
-              return result.hasIndexInParent();
-            }
-
-            // required
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData
-            // logData = 3;
-            public boolean hasLogData() {
-              return result.hasLogData();
-            }
-
-            // required uint32 parentLogHandle = 1;
-            public boolean hasParentLogHandle() {
-              return result.hasParentLogHandle();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
+            
             public Builder mergeFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
               while (true) {
                 int tag = input.readTag();
                 switch (tag) {
@@ -3683,7 +2701,411 @@
                     return this;
                   default: {
                     if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                  case 10: {
+                    setSummary(input.readString());
+                    break;
+                  }
+                  case 18: {
+                    setLevel(input.readString());
+                    break;
+                  }
+                  case 26: {
+                    setDetails(input.readString());
+                    break;
+                  }
+                  case 34: {
+                    com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.newBuilder();
+                    if (hasHelpInfo()) {
+                      subBuilder.mergeFrom(getHelpInfo());
+                    }
+                    input.readMessage(subBuilder, extensionRegistry);
+                    setHelpInfo(subBuilder.buildPartial());
+                    break;
+                  }
+                }
+              }
+            }
+            
+            
+            // required string summary = 1;
+            public boolean hasSummary() {
+              return result.hasSummary();
+            }
+            public java.lang.String getSummary() {
+              return result.getSummary();
+            }
+            public Builder setSummary(java.lang.String value) {
+              if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasSummary = true;
+              result.summary_ = value;
+              return this;
+            }
+            public Builder clearSummary() {
+              result.hasSummary = false;
+              result.summary_ = getDefaultInstance().getSummary();
+              return this;
+            }
+            
+            // optional string level = 2;
+            public boolean hasLevel() {
+              return result.hasLevel();
+            }
+            public java.lang.String getLevel() {
+              return result.getLevel();
+            }
+            public Builder setLevel(java.lang.String value) {
+              if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasLevel = true;
+              result.level_ = value;
+              return this;
+            }
+            public Builder clearLevel() {
+              result.hasLevel = false;
+              result.level_ = getDefaultInstance().getLevel();
+              return this;
+            }
+            
+            // optional string details = 3;
+            public boolean hasDetails() {
+              return result.hasDetails();
+            }
+            public java.lang.String getDetails() {
+              return result.getDetails();
+            }
+            public Builder setDetails(java.lang.String value) {
+              if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasDetails = true;
+              result.details_ = value;
+              return this;
+            }
+            public Builder clearDetails() {
+              result.hasDetails = false;
+              result.details_ = getDefaultInstance().getDetails();
+              return this;
+            }
+            
+            // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData.HelpInfo helpInfo = 4;
+            public boolean hasHelpInfo() {
+              return result.hasHelpInfo();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo getHelpInfo() {
+              return result.getHelpInfo();
+            }
+            public Builder setHelpInfo(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo value) {
+              if (value == null) {
+                throw new NullPointerException();
+              }
+              result.hasHelpInfo = true;
+              result.helpInfo_ = value;
+              return this;
+            }
+            public Builder setHelpInfo(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.Builder builderForValue) {
+              result.hasHelpInfo = true;
+              result.helpInfo_ = builderForValue.build();
+              return this;
+            }
+            public Builder mergeHelpInfo(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo value) {
+              if (result.hasHelpInfo() &&
+                  result.helpInfo_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance()) {
+                result.helpInfo_ =
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.newBuilder(result.helpInfo_).mergeFrom(value).buildPartial();
+              } else {
+                result.helpInfo_ = value;
+              }
+              result.hasHelpInfo = true;
+              return this;
+            }
+            public Builder clearHelpInfo() {
+              result.hasHelpInfo = false;
+              result.helpInfo_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance();
+              return this;
+            }
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+          }
+        }
+        
+        public static final class AddLogBranch extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use AddLogBranch.newBuilder() to construct.
+          private AddLogBranch() {}
+          
+          private static final AddLogBranch defaultInstance = new AddLogBranch();
+          public static AddLogBranch getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public AddLogBranch getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_fieldAccessorTable;
+          }
+          
+          // required uint32 parentLogHandle = 1;
+          public static final int PARENTLOGHANDLE_FIELD_NUMBER = 1;
+          private boolean hasParentLogHandle;
+          private int parentLogHandle_ = 0;
+          public boolean hasParentLogHandle() { return hasParentLogHandle; }
+          public int getParentLogHandle() { return parentLogHandle_; }
+          
+          // required uint32 indexInParent = 2;
+          public static final int INDEXINPARENT_FIELD_NUMBER = 2;
+          private boolean hasIndexInParent;
+          private int indexInParent_ = 0;
+          public boolean hasIndexInParent() { return hasIndexInParent; }
+          public int getIndexInParent() { return indexInParent_; }
+          
+          // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData logData = 3;
+          public static final int LOGDATA_FIELD_NUMBER = 3;
+          private boolean hasLogData;
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
+          public boolean hasLogData() { return hasLogData; }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() { return logData_; }
+          
+          public final boolean isInitialized() {
+            if (!hasParentLogHandle) return false;
+            if (!hasIndexInParent) return false;
+            if (!hasLogData) return false;
+            if (!getLogData().isInitialized()) return false;
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            if (hasParentLogHandle()) {
+              output.writeUInt32(1, getParentLogHandle());
+            }
+            if (hasIndexInParent()) {
+              output.writeUInt32(2, getIndexInParent());
+            }
+            if (hasLogData()) {
+              output.writeMessage(3, getLogData());
+            }
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            if (hasParentLogHandle()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeUInt32Size(1, getParentLogHandle());
+            }
+            if (hasIndexInParent()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeUInt32Size(2, getIndexInParent());
+            }
+            if (hasLogData()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(3, getLogData());
+            }
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
+          }
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch();
+              return builder;
+            }
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch internalGetResult() {
+              return result;
+            }
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance()) return this;
+              if (other.hasParentLogHandle()) {
+                setParentLogHandle(other.getParentLogHandle());
+              }
+              if (other.hasIndexInParent()) {
+                setIndexInParent(other.getIndexInParent());
+              }
+              if (other.hasLogData()) {
+                mergeLogData(other.getLogData());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
                       this.setUnknownFields(unknownFields.build());
                       return this;
                     }
@@ -3709,54 +3131,52 @@
                 }
               }
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            
+            // required uint32 parentLogHandle = 1;
+            public boolean hasParentLogHandle() {
+              return result.hasParentLogHandle();
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance())
-                return this;
-              if (other.hasParentLogHandle()) {
-                setParentLogHandle(other.getParentLogHandle());
-              }
-              if (other.hasIndexInParent()) {
-                setIndexInParent(other.getIndexInParent());
-              }
-              if (other.hasLogData()) {
-                mergeLogData(other.getLogData());
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
+            public int getParentLogHandle() {
+              return result.getParentLogHandle();
+            }
+            public Builder setParentLogHandle(int value) {
+              result.hasParentLogHandle = true;
+              result.parentLogHandle_ = value;
               return this;
             }
-
-            public Builder mergeLogData(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
-              if (result.hasLogData()
-                  && result.logData_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance()) {
-                result.logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.newBuilder(
-                    result.logData_).mergeFrom(value).buildPartial();
-              } else {
-                result.logData_ = value;
-              }
-              result.hasLogData = true;
+            public Builder clearParentLogHandle() {
+              result.hasParentLogHandle = false;
+              result.parentLogHandle_ = 0;
               return this;
             }
-
+            
+            // required uint32 indexInParent = 2;
+            public boolean hasIndexInParent() {
+              return result.hasIndexInParent();
+            }
+            public int getIndexInParent() {
+              return result.getIndexInParent();
+            }
             public Builder setIndexInParent(int value) {
               result.hasIndexInParent = true;
               result.indexInParent_ = value;
               return this;
             }
-
-            public Builder setLogData(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
+            public Builder clearIndexInParent() {
+              result.hasIndexInParent = false;
+              result.indexInParent_ = 0;
+              return this;
+            }
+            
+            // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData logData = 3;
+            public boolean hasLogData() {
+              return result.hasLogData();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() {
+              return result.getLogData();
+            }
+            public Builder setLogData(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
               if (value == null) {
                 throw new NullPointerException();
               }
@@ -3764,349 +3184,292 @@
               result.logData_ = value;
               return this;
             }
-
-            public Builder setLogData(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.Builder builderForValue) {
+            public Builder setLogData(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.Builder builderForValue) {
               result.hasLogData = true;
               result.logData_ = builderForValue.build();
               return this;
             }
-
-            public Builder setParentLogHandle(int value) {
-              result.hasParentLogHandle = true;
-              result.parentLogHandle_ = value;
+            public Builder mergeLogData(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
+              if (result.hasLogData() &&
+                  result.logData_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance()) {
+                result.logData_ =
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.newBuilder(result.logData_).mergeFrom(value).buildPartial();
+              } else {
+                result.logData_ = value;
+              }
+              result.hasLogData = true;
               return this;
             }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
+            public Builder clearLogData() {
+              result.hasLogData = false;
+              result.logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
+              return this;
             }
           }
-
-          private static final AddLogBranch defaultInstance = new AddLogBranch();
-          // required uint32 parentLogHandle = 1;
-          public static final int PARENTLOGHANDLE_FIELD_NUMBER = 1;
-
-          // required uint32 indexInParent = 2;
-          public static final int INDEXINPARENT_FIELD_NUMBER = 2;
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
           }
-
-          public static AddLogBranch getDefaultInstance() {
+        }
+        
+        public static final class AddLogEntry extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use AddLogEntry.newBuilder() to construct.
+          private AddLogEntry() {}
+          
+          private static final AddLogEntry defaultInstance = new AddLogEntry();
+          public static AddLogEntry getDefaultInstance() {
             return defaultInstance;
           }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor;
+          
+          public AddLogEntry getDefaultInstanceForType() {
+            return defaultInstance;
           }
-
-          public static Builder newBuilder() {
-            return Builder.create();
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor;
           }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch prototype) {
-            return newBuilder().mergeFrom(prototype);
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_fieldAccessorTable;
           }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private boolean hasParentLogHandle;
-
-          private int parentLogHandle_ = 0;
-
-          private boolean hasIndexInParent;
-
-          private int indexInParent_ = 0;
-          // required
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData
-          // logData = 3;
+          
+          // required uint32 logHandle = 1;
+          public static final int LOGHANDLE_FIELD_NUMBER = 1;
+          private boolean hasLogHandle;
+          private int logHandle_ = 0;
+          public boolean hasLogHandle() { return hasLogHandle; }
+          public int getLogHandle() { return logHandle_; }
+          
+          // required uint32 indexInLog = 2;
+          public static final int INDEXINLOG_FIELD_NUMBER = 2;
+          private boolean hasIndexInLog;
+          private int indexInLog_ = 0;
+          public boolean hasIndexInLog() { return hasIndexInLog; }
+          public int getIndexInLog() { return indexInLog_; }
+          
+          // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData logData = 3;
           public static final int LOGDATA_FIELD_NUMBER = 3;
-
           private boolean hasLogData;
           private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
-          private int memoizedSerializedSize = -1;
-
-          // Use AddLogBranch.newBuilder() to construct.
-          private AddLogBranch() {
-          }
-
-          public AddLogBranch getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getIndexInParent() {
-            return indexInParent_;
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() {
-            return logData_;
-          }
-
-          public int getParentLogHandle() {
-            return parentLogHandle_;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            if (hasParentLogHandle()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-                  1, getParentLogHandle());
-            }
-            if (hasIndexInParent()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-                  2, getIndexInParent());
-            }
-            if (hasLogData()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  3, getLogData());
-            }
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public boolean hasIndexInParent() {
-            return hasIndexInParent;
-          }
-
-          public boolean hasLogData() {
-            return hasLogData;
-          }
-
-          public boolean hasParentLogHandle() {
-            return hasParentLogHandle;
-          }
-
+          public boolean hasLogData() { return hasLogData; }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() { return logData_; }
+          
           public final boolean isInitialized() {
-            if (!hasParentLogHandle)
-              return false;
-            if (!hasIndexInParent)
-              return false;
-            if (!hasLogData)
-              return false;
-            if (!getLogData().isInitialized())
-              return false;
+            if (!hasLogHandle) return false;
+            if (!hasIndexInLog) return false;
+            if (!hasLogData) return false;
+            if (!getLogData().isInitialized()) return false;
             return true;
           }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            if (hasParentLogHandle()) {
-              output.writeUInt32(1, getParentLogHandle());
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            if (hasLogHandle()) {
+              output.writeUInt32(1, getLogHandle());
             }
-            if (hasIndexInParent()) {
-              output.writeUInt32(2, getIndexInParent());
+            if (hasIndexInLog()) {
+              output.writeUInt32(2, getIndexInLog());
             }
             if (hasLogData()) {
               output.writeMessage(3, getLogData());
             }
             getUnknownFields().writeTo(output);
           }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_fieldAccessorTable;
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            if (hasLogHandle()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeUInt32Size(1, getLogHandle());
+            }
+            if (hasIndexInLog()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeUInt32Size(2, getIndexInLog());
+            }
+            if (hasLogData()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(3, getLogData());
+            }
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
           }
-        }
-        public static final class AddLogEntry extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
           public static final class Builder extends
               com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.newBuilder()
+            private Builder() {}
+            
             private static Builder create() {
               Builder builder = new Builder();
               builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry();
               return builder;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.newBuilder()
-            private Builder() {
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry internalGetResult() {
+              return result;
             }
-
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry build() {
               if (result != null && !isInitialized()) {
                 throw newUninitializedMessageException(result);
               }
               return buildPartial();
             }
-
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry buildPartial() {
               if (result == null) {
                 throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
+                  "build() has already been called on this Builder.");
               }
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry returnMe = result;
               result = null;
               return returnMe;
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
               }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry();
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance()) return this;
+              if (other.hasLogHandle()) {
+                setLogHandle(other.getLogHandle());
+              }
+              if (other.hasIndexInLog()) {
+                setIndexInLog(other.getIndexInLog());
+              }
+              if (other.hasLogData()) {
+                mergeLogData(other.getLogData());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
               return this;
             }
-
-            public Builder clearIndexInLog() {
-              result.hasIndexInLog = false;
-              result.indexInLog_ = 0;
-              return this;
-            }
-
-            public Builder clearLogData() {
-              result.hasLogData = false;
-              result.logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
-              return this;
-            }
-
-            public Builder clearLogHandle() {
-              result.hasLogHandle = false;
-              result.logHandle_ = 0;
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDescriptor();
-            }
-
-            public int getIndexInLog() {
-              return result.getIndexInLog();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() {
-              return result.getLogData();
-            }
-
-            public int getLogHandle() {
-              return result.getLogHandle();
-            }
-
-            // required uint32 indexInLog = 2;
-            public boolean hasIndexInLog() {
-              return result.hasIndexInLog();
-            }
-
-            // required
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData
-            // logData = 3;
-            public boolean hasLogData() {
-              return result.hasLogData();
-            }
-
-            // required uint32 logHandle = 1;
-            public boolean hasLogHandle() {
-              return result.hasLogHandle();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
+            
             public Builder mergeFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
               while (true) {
                 int tag = input.readTag();
                 switch (tag) {
@@ -4115,7 +3478,7 @@
                     return this;
                   default: {
                     if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
+                                           extensionRegistry, tag)) {
                       this.setUnknownFields(unknownFields.build());
                       return this;
                     }
@@ -4141,54 +3504,52 @@
                 }
               }
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            
+            // required uint32 logHandle = 1;
+            public boolean hasLogHandle() {
+              return result.hasLogHandle();
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance())
-                return this;
-              if (other.hasLogHandle()) {
-                setLogHandle(other.getLogHandle());
-              }
-              if (other.hasIndexInLog()) {
-                setIndexInLog(other.getIndexInLog());
-              }
-              if (other.hasLogData()) {
-                mergeLogData(other.getLogData());
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
+            public int getLogHandle() {
+              return result.getLogHandle();
+            }
+            public Builder setLogHandle(int value) {
+              result.hasLogHandle = true;
+              result.logHandle_ = value;
               return this;
             }
-
-            public Builder mergeLogData(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
-              if (result.hasLogData()
-                  && result.logData_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance()) {
-                result.logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.newBuilder(
-                    result.logData_).mergeFrom(value).buildPartial();
-              } else {
-                result.logData_ = value;
-              }
-              result.hasLogData = true;
+            public Builder clearLogHandle() {
+              result.hasLogHandle = false;
+              result.logHandle_ = 0;
               return this;
             }
-
+            
+            // required uint32 indexInLog = 2;
+            public boolean hasIndexInLog() {
+              return result.hasIndexInLog();
+            }
+            public int getIndexInLog() {
+              return result.getIndexInLog();
+            }
             public Builder setIndexInLog(int value) {
               result.hasIndexInLog = true;
               result.indexInLog_ = value;
               return this;
             }
-
-            public Builder setLogData(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
+            public Builder clearIndexInLog() {
+              result.hasIndexInLog = false;
+              result.indexInLog_ = 0;
+              return this;
+            }
+            
+            // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData logData = 3;
+            public boolean hasLogData() {
+              return result.hasLogData();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() {
+              return result.getLogData();
+            }
+            public Builder setLogData(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
               if (value == null) {
                 throw new NullPointerException();
               }
@@ -4196,468 +3557,964 @@
               result.logData_ = value;
               return this;
             }
-
-            public Builder setLogData(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.Builder builderForValue) {
+            public Builder setLogData(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.Builder builderForValue) {
               result.hasLogData = true;
               result.logData_ = builderForValue.build();
               return this;
             }
-
-            public Builder setLogHandle(int value) {
-              result.hasLogHandle = true;
-              result.logHandle_ = value;
+            public Builder mergeLogData(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData value) {
+              if (result.hasLogData() &&
+                  result.logData_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance()) {
+                result.logData_ =
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.newBuilder(result.logData_).mergeFrom(value).buildPartial();
+              } else {
+                result.logData_ = value;
+              }
+              result.hasLogData = true;
               return this;
             }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
+            public Builder clearLogData() {
+              result.hasLogData = false;
+              result.logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
+              return this;
             }
           }
-
-          private static final AddLogEntry defaultInstance = new AddLogEntry();
-          // required uint32 logHandle = 1;
-          public static final int LOGHANDLE_FIELD_NUMBER = 1;
-
-          // required uint32 indexInLog = 2;
-          public static final int INDEXINLOG_FIELD_NUMBER = 2;
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
           }
-
-          public static AddLogEntry getDefaultInstance() {
+        }
+        
+        public static final class DisconnectLog extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use DisconnectLog.newBuilder() to construct.
+          private DisconnectLog() {}
+          
+          private static final DisconnectLog defaultInstance = new DisconnectLog();
+          public static DisconnectLog getDefaultInstance() {
             return defaultInstance;
           }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor;
+          
+          public DisconnectLog getDefaultInstanceForType() {
+            return defaultInstance;
           }
-
-          public static Builder newBuilder() {
-            return Builder.create();
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor;
           }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry prototype) {
-            return newBuilder().mergeFrom(prototype);
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_fieldAccessorTable;
           }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
+          
+          // required uint32 logHandle = 1;
+          public static final int LOGHANDLE_FIELD_NUMBER = 1;
           private boolean hasLogHandle;
-
           private int logHandle_ = 0;
-
-          private boolean hasIndexInLog;
-
-          private int indexInLog_ = 0;
-          // required
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData
-          // logData = 3;
-          public static final int LOGDATA_FIELD_NUMBER = 3;
-
-          private boolean hasLogData;
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData logData_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
+          public boolean hasLogHandle() { return hasLogHandle; }
+          public int getLogHandle() { return logHandle_; }
+          
+          public final boolean isInitialized() {
+            if (!hasLogHandle) return false;
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            if (hasLogHandle()) {
+              output.writeUInt32(1, getLogHandle());
+            }
+            getUnknownFields().writeTo(output);
+          }
+          
           private int memoizedSerializedSize = -1;
-
-          // Use AddLogEntry.newBuilder() to construct.
-          private AddLogEntry() {
-          }
-
-          public AddLogEntry getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getIndexInLog() {
-            return indexInLog_;
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getLogData() {
-            return logData_;
-          }
-
-          public int getLogHandle() {
-            return logHandle_;
-          }
-
           public int getSerializedSize() {
             int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
+            if (size != -1) return size;
+          
             size = 0;
             if (hasLogHandle()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-                  1, getLogHandle());
-            }
-            if (hasIndexInLog()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-                  2, getIndexInLog());
-            }
-            if (hasLogData()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  3, getLogData());
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeUInt32Size(1, getLogHandle());
             }
             size += getUnknownFields().getSerializedSize();
             memoizedSerializedSize = size;
             return size;
           }
-
-          public boolean hasIndexInLog() {
-            return hasIndexInLog;
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public boolean hasLogData() {
-            return hasLogData;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-
-          public boolean hasLogHandle() {
-            return hasLogHandle;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog();
+              return builder;
+            }
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog internalGetResult() {
+              return result;
+            }
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance()) return this;
+              if (other.hasLogHandle()) {
+                setLogHandle(other.getLogHandle());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                  case 8: {
+                    setLogHandle(input.readUInt32());
+                    break;
+                  }
+                }
+              }
+            }
+            
+            
+            // required uint32 logHandle = 1;
+            public boolean hasLogHandle() {
+              return result.hasLogHandle();
+            }
+            public int getLogHandle() {
+              return result.getLogHandle();
+            }
+            public Builder setLogHandle(int value) {
+              result.hasLogHandle = true;
+              result.logHandle_ = value;
+              return this;
+            }
+            public Builder clearLogHandle() {
+              result.hasLogHandle = false;
+              result.logHandle_ = 0;
+              return this;
+            }
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+          }
+        }
+        
+        public static final class Initialize extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use Initialize.newBuilder() to construct.
+          private Initialize() {}
+          
+          private static final Initialize defaultInstance = new Initialize();
+          public static Initialize getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public Initialize getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_Initialize_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_Initialize_fieldAccessorTable;
+          }
+          
+          // optional string clientId = 1;
+          public static final int CLIENTID_FIELD_NUMBER = 1;
+          private boolean hasClientId;
+          private java.lang.String clientId_ = "";
+          public boolean hasClientId() { return hasClientId; }
+          public java.lang.String getClientId() { return clientId_; }
+          
+          // optional string devModeQueryParam = 2;
+          public static final int DEVMODEQUERYPARAM_FIELD_NUMBER = 2;
+          private boolean hasDevModeQueryParam;
+          private java.lang.String devModeQueryParam_ = "";
+          public boolean hasDevModeQueryParam() { return hasDevModeQueryParam; }
+          public java.lang.String getDevModeQueryParam() { return devModeQueryParam_; }
+          
+          // optional sint32 webServerPort = 3;
+          public static final int WEBSERVERPORT_FIELD_NUMBER = 3;
+          private boolean hasWebServerPort;
+          private int webServerPort_ = 0;
+          public boolean hasWebServerPort() { return hasWebServerPort; }
+          public int getWebServerPort() { return webServerPort_; }
+          
           public final boolean isInitialized() {
-            if (!hasLogHandle)
-              return false;
-            if (!hasIndexInLog)
-              return false;
-            if (!hasLogData)
-              return false;
-            if (!getLogData().isInitialized())
-              return false;
             return true;
           }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            if (hasLogHandle()) {
-              output.writeUInt32(1, getLogHandle());
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            if (hasClientId()) {
+              output.writeString(1, getClientId());
             }
-            if (hasIndexInLog()) {
-              output.writeUInt32(2, getIndexInLog());
+            if (hasDevModeQueryParam()) {
+              output.writeString(2, getDevModeQueryParam());
             }
-            if (hasLogData()) {
-              output.writeMessage(3, getLogData());
+            if (hasWebServerPort()) {
+              output.writeSInt32(3, getWebServerPort());
             }
             getUnknownFields().writeTo(output);
           }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_fieldAccessorTable;
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            if (hasClientId()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeStringSize(1, getClientId());
+            }
+            if (hasDevModeQueryParam()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeStringSize(2, getDevModeQueryParam());
+            }
+            if (hasWebServerPort()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeSInt32Size(3, getWebServerPort());
+            }
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
+          }
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize();
+              return builder;
+            }
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize internalGetResult() {
+              return result;
+            }
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.getDefaultInstance()) return this;
+              if (other.hasClientId()) {
+                setClientId(other.getClientId());
+              }
+              if (other.hasDevModeQueryParam()) {
+                setDevModeQueryParam(other.getDevModeQueryParam());
+              }
+              if (other.hasWebServerPort()) {
+                setWebServerPort(other.getWebServerPort());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                  case 10: {
+                    setClientId(input.readString());
+                    break;
+                  }
+                  case 18: {
+                    setDevModeQueryParam(input.readString());
+                    break;
+                  }
+                  case 24: {
+                    setWebServerPort(input.readSInt32());
+                    break;
+                  }
+                }
+              }
+            }
+            
+            
+            // optional string clientId = 1;
+            public boolean hasClientId() {
+              return result.hasClientId();
+            }
+            public java.lang.String getClientId() {
+              return result.getClientId();
+            }
+            public Builder setClientId(java.lang.String value) {
+              if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasClientId = true;
+              result.clientId_ = value;
+              return this;
+            }
+            public Builder clearClientId() {
+              result.hasClientId = false;
+              result.clientId_ = getDefaultInstance().getClientId();
+              return this;
+            }
+            
+            // optional string devModeQueryParam = 2;
+            public boolean hasDevModeQueryParam() {
+              return result.hasDevModeQueryParam();
+            }
+            public java.lang.String getDevModeQueryParam() {
+              return result.getDevModeQueryParam();
+            }
+            public Builder setDevModeQueryParam(java.lang.String value) {
+              if (value == null) {
+    throw new NullPointerException();
+  }
+  result.hasDevModeQueryParam = true;
+              result.devModeQueryParam_ = value;
+              return this;
+            }
+            public Builder clearDevModeQueryParam() {
+              result.hasDevModeQueryParam = false;
+              result.devModeQueryParam_ = getDefaultInstance().getDevModeQueryParam();
+              return this;
+            }
+            
+            // optional sint32 webServerPort = 3;
+            public boolean hasWebServerPort() {
+              return result.hasWebServerPort();
+            }
+            public int getWebServerPort() {
+              return result.getWebServerPort();
+            }
+            public Builder setWebServerPort(int value) {
+              result.hasWebServerPort = true;
+              result.webServerPort_ = value;
+              return this;
+            }
+            public Builder clearWebServerPort() {
+              result.hasWebServerPort = false;
+              result.webServerPort_ = 0;
+              return this;
+            }
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
           }
         }
-
+        
+        // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType requestType = 1;
+        public static final int REQUESTTYPE_FIELD_NUMBER = 1;
+        private boolean hasRequestType;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
+        public boolean hasRequestType() { return hasRequestType; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getRequestType() { return requestType_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.CapabilityExchange capabilityExchange = 2;
+        public static final int CAPABILITYEXCHANGE_FIELD_NUMBER = 2;
+        private boolean hasCapabilityExchange;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance();
+        public boolean hasCapabilityExchange() { return hasCapabilityExchange; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange getCapabilityExchange() { return capabilityExchange_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog addLog = 3;
+        public static final int ADDLOG_FIELD_NUMBER = 3;
+        private boolean hasAddLog;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance();
+        public boolean hasAddLog() { return hasAddLog; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog getAddLog() { return addLog_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogBranch addLogBranch = 4;
+        public static final int ADDLOGBRANCH_FIELD_NUMBER = 4;
+        private boolean hasAddLogBranch;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance();
+        public boolean hasAddLogBranch() { return hasAddLogBranch; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch getAddLogBranch() { return addLogBranch_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogEntry addLogEntry = 5;
+        public static final int ADDLOGENTRY_FIELD_NUMBER = 5;
+        private boolean hasAddLogEntry;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry addLogEntry_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance();
+        public boolean hasAddLogEntry() { return hasAddLogEntry; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry getAddLogEntry() { return addLogEntry_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.DisconnectLog disconnectLog = 6;
+        public static final int DISCONNECTLOG_FIELD_NUMBER = 6;
+        private boolean hasDisconnectLog;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog disconnectLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance();
+        public boolean hasDisconnectLog() { return hasDisconnectLog; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog getDisconnectLog() { return disconnectLog_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.Initialize initialize = 7;
+        public static final int INITIALIZE_FIELD_NUMBER = 7;
+        private boolean hasInitialize;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize initialize_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.getDefaultInstance();
+        public boolean hasInitialize() { return hasInitialize; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize getInitialize() { return initialize_; }
+        
+        public final boolean isInitialized() {
+          if (!hasRequestType) return false;
+          if (hasAddLog()) {
+            if (!getAddLog().isInitialized()) return false;
+          }
+          if (hasAddLogBranch()) {
+            if (!getAddLogBranch().isInitialized()) return false;
+          }
+          if (hasAddLogEntry()) {
+            if (!getAddLogEntry().isInitialized()) return false;
+          }
+          if (hasDisconnectLog()) {
+            if (!getDisconnectLog().isInitialized()) return false;
+          }
+          return true;
+        }
+        
+        public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                            throws java.io.IOException {
+          if (hasRequestType()) {
+            output.writeEnum(1, getRequestType().getNumber());
+          }
+          if (hasCapabilityExchange()) {
+            output.writeMessage(2, getCapabilityExchange());
+          }
+          if (hasAddLog()) {
+            output.writeMessage(3, getAddLog());
+          }
+          if (hasAddLogBranch()) {
+            output.writeMessage(4, getAddLogBranch());
+          }
+          if (hasAddLogEntry()) {
+            output.writeMessage(5, getAddLogEntry());
+          }
+          if (hasDisconnectLog()) {
+            output.writeMessage(6, getDisconnectLog());
+          }
+          if (hasInitialize()) {
+            output.writeMessage(7, getInitialize());
+          }
+          getUnknownFields().writeTo(output);
+        }
+        
+        private int memoizedSerializedSize = -1;
+        public int getSerializedSize() {
+          int size = memoizedSerializedSize;
+          if (size != -1) return size;
+        
+          size = 0;
+          if (hasRequestType()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeEnumSize(1, getRequestType().getNumber());
+          }
+          if (hasCapabilityExchange()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(2, getCapabilityExchange());
+          }
+          if (hasAddLog()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(3, getAddLog());
+          }
+          if (hasAddLogBranch()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(4, getAddLogBranch());
+          }
+          if (hasAddLogEntry()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(5, getAddLogEntry());
+          }
+          if (hasDisconnectLog()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(6, getDisconnectLog());
+          }
+          if (hasInitialize()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(7, getInitialize());
+          }
+          size += getUnknownFields().getSerializedSize();
+          memoizedSerializedSize = size;
+          return size;
+        }
+        
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(byte[] data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
+            byte[] data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseDelimitedFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseDelimitedFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        
+        public static Builder newBuilder() { return Builder.create(); }
+        public Builder newBuilderForType() { return newBuilder(); }
+        public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest prototype) {
+          return newBuilder().mergeFrom(prototype);
+        }
+        public Builder toBuilder() { return newBuilder(this); }
+        
         public static final class Builder extends
             com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest result;
+          
+          // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.newBuilder()
+          private Builder() {}
+          
           private static Builder create() {
             Builder builder = new Builder();
             builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest();
             return builder;
           }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest result;
-
-          // Construct using
-          // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.newBuilder()
-          private Builder() {
+          
+          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest internalGetResult() {
+            return result;
           }
-
+          
+          public Builder clear() {
+            if (result == null) {
+              throw new IllegalStateException(
+                "Cannot call clear() after build().");
+            }
+            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest();
+            return this;
+          }
+          
+          public Builder clone() {
+            return create().mergeFrom(result);
+          }
+          
+          public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptorForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDescriptor();
+          }
+          
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest getDefaultInstanceForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance();
+          }
+          
+          public boolean isInitialized() {
+            return result.isInitialized();
+          }
           public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest build() {
             if (result != null && !isInitialized()) {
               throw newUninitializedMessageException(result);
             }
             return buildPartial();
           }
-
+          
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest buildParsed()
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            if (!isInitialized()) {
+              throw newUninitializedMessageException(
+                result).asInvalidProtocolBufferException();
+            }
+            return buildPartial();
+          }
+          
           public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest buildPartial() {
             if (result == null) {
               throw new IllegalStateException(
-                  "build() has already been called on this Builder.");
+                "build() has already been called on this Builder.");
             }
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest returnMe = result;
             result = null;
             return returnMe;
           }
-
-          public Builder clear() {
-            if (result == null) {
-              throw new IllegalStateException(
-                  "Cannot call clear() after build().");
-            }
-            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest();
-            return this;
-          }
-
-          public Builder clearAddLog() {
-            result.hasAddLog = false;
-            result.addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearAddLogBranch() {
-            result.hasAddLogBranch = false;
-            result.addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearAddLogEntry() {
-            result.hasAddLogEntry = false;
-            result.addLogEntry_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearCapabilityExchange() {
-            result.hasCapabilityExchange = false;
-            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearDisconnectLog() {
-            result.hasDisconnectLog = false;
-            result.disconnectLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearRequestType() {
-            result.hasRequestType = false;
-            result.requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
-            return this;
-          }
-
-          public Builder clone() {
-            return create().mergeFrom(result);
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog getAddLog() {
-            return result.getAddLog();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch getAddLogBranch() {
-            return result.getAddLogBranch();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry getAddLogEntry() {
-            return result.getAddLogEntry();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange getCapabilityExchange() {
-            return result.getCapabilityExchange();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest getDefaultInstanceForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance();
-          }
-
-          public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDescriptor();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog getDisconnectLog() {
-            return result.getDisconnectLog();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getRequestType() {
-            return result.getRequestType();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog
-          // addLog = 3;
-          public boolean hasAddLog() {
-            return result.hasAddLog();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogBranch
-          // addLogBranch = 4;
-          public boolean hasAddLogBranch() {
-            return result.hasAddLogBranch();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogEntry
-          // addLogEntry = 5;
-          public boolean hasAddLogEntry() {
-            return result.hasAddLogEntry();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.CapabilityExchange
-          // capabilityExchange = 2;
-          public boolean hasCapabilityExchange() {
-            return result.hasCapabilityExchange();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.DisconnectLog
-          // disconnectLog = 6;
-          public boolean hasDisconnectLog() {
-            return result.hasDisconnectLog();
-          }
-
-          // required
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType
-          // requestType = 1;
-          public boolean hasRequestType() {
-            return result.hasRequestType();
-          }
-
-          public boolean isInitialized() {
-            return result.isInitialized();
-          }
-
-          public Builder mergeAddLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog value) {
-            if (result.hasAddLog()
-                && result.addLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance()) {
-              result.addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.newBuilder(
-                  result.addLog_).mergeFrom(value).buildPartial();
+          
+          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest) {
+              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest)other);
             } else {
-              result.addLog_ = value;
+              super.mergeFrom(other);
+              return this;
             }
-            result.hasAddLog = true;
+          }
+          
+          public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest other) {
+            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance()) return this;
+            if (other.hasRequestType()) {
+              setRequestType(other.getRequestType());
+            }
+            if (other.hasCapabilityExchange()) {
+              mergeCapabilityExchange(other.getCapabilityExchange());
+            }
+            if (other.hasAddLog()) {
+              mergeAddLog(other.getAddLog());
+            }
+            if (other.hasAddLogBranch()) {
+              mergeAddLogBranch(other.getAddLogBranch());
+            }
+            if (other.hasAddLogEntry()) {
+              mergeAddLogEntry(other.getAddLogEntry());
+            }
+            if (other.hasDisconnectLog()) {
+              mergeDisconnectLog(other.getDisconnectLog());
+            }
+            if (other.hasInitialize()) {
+              mergeInitialize(other.getInitialize());
+            }
+            this.mergeUnknownFields(other.getUnknownFields());
             return this;
           }
-
-          public Builder mergeAddLogBranch(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch value) {
-            if (result.hasAddLogBranch()
-                && result.addLogBranch_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance()) {
-              result.addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.newBuilder(
-                  result.addLogBranch_).mergeFrom(value).buildPartial();
-            } else {
-              result.addLogBranch_ = value;
-            }
-            result.hasAddLogBranch = true;
-            return this;
-          }
-
-          public Builder mergeAddLogEntry(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry value) {
-            if (result.hasAddLogEntry()
-                && result.addLogEntry_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance()) {
-              result.addLogEntry_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.newBuilder(
-                  result.addLogEntry_).mergeFrom(value).buildPartial();
-            } else {
-              result.addLogEntry_ = value;
-            }
-            result.hasAddLogEntry = true;
-            return this;
-          }
-
-          public Builder mergeCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange value) {
-            if (result.hasCapabilityExchange()
-                && result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance()) {
-              result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.newBuilder(
-                  result.capabilityExchange_).mergeFrom(value).buildPartial();
-            } else {
-              result.capabilityExchange_ = value;
-            }
-            result.hasCapabilityExchange = true;
-            return this;
-          }
-
-          public Builder mergeDisconnectLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog value) {
-            if (result.hasDisconnectLog()
-                && result.disconnectLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance()) {
-              result.disconnectLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.newBuilder(
-                  result.disconnectLog_).mergeFrom(value).buildPartial();
-            } else {
-              result.disconnectLog_ = value;
-            }
-            result.hasDisconnectLog = true;
-            return this;
-          }
-
+          
           public Builder mergeFrom(
               com.google.gwt.dev.protobuf.CodedInputStream input,
               com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
               throws java.io.IOException {
-            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+              com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                this.getUnknownFields());
             while (true) {
               int tag = input.readTag();
               switch (tag) {
@@ -4666,7 +4523,7 @@
                   return this;
                 default: {
                   if (!parseUnknownField(input, unknownFields,
-                      extensionRegistry, tag)) {
+                                         extensionRegistry, tag)) {
                     this.setUnknownFields(unknownFields.build());
                     return this;
                   }
@@ -4727,132 +4584,28 @@
                   setDisconnectLog(subBuilder.buildPartial());
                   break;
                 }
+                case 58: {
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.newBuilder();
+                  if (hasInitialize()) {
+                    subBuilder.mergeFrom(getInitialize());
+                  }
+                  input.readMessage(subBuilder, extensionRegistry);
+                  setInitialize(subBuilder.buildPartial());
+                  break;
+                }
               }
             }
           }
-
-          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest) {
-              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest) other);
-            } else {
-              super.mergeFrom(other);
-              return this;
-            }
+          
+          
+          // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType requestType = 1;
+          public boolean hasRequestType() {
+            return result.hasRequestType();
           }
-
-          public Builder mergeFrom(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest other) {
-            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance())
-              return this;
-            if (other.hasRequestType()) {
-              setRequestType(other.getRequestType());
-            }
-            if (other.hasCapabilityExchange()) {
-              mergeCapabilityExchange(other.getCapabilityExchange());
-            }
-            if (other.hasAddLog()) {
-              mergeAddLog(other.getAddLog());
-            }
-            if (other.hasAddLogBranch()) {
-              mergeAddLogBranch(other.getAddLogBranch());
-            }
-            if (other.hasAddLogEntry()) {
-              mergeAddLogEntry(other.getAddLogEntry());
-            }
-            if (other.hasDisconnectLog()) {
-              mergeDisconnectLog(other.getDisconnectLog());
-            }
-            this.mergeUnknownFields(other.getUnknownFields());
-            return this;
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getRequestType() {
+            return result.getRequestType();
           }
-
-          public Builder setAddLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasAddLog = true;
-            result.addLog_ = value;
-            return this;
-          }
-
-          public Builder setAddLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.Builder builderForValue) {
-            result.hasAddLog = true;
-            result.addLog_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setAddLogBranch(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasAddLogBranch = true;
-            result.addLogBranch_ = value;
-            return this;
-          }
-
-          public Builder setAddLogBranch(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.Builder builderForValue) {
-            result.hasAddLogBranch = true;
-            result.addLogBranch_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setAddLogEntry(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasAddLogEntry = true;
-            result.addLogEntry_ = value;
-            return this;
-          }
-
-          public Builder setAddLogEntry(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.Builder builderForValue) {
-            result.hasAddLogEntry = true;
-            result.addLogEntry_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = value;
-            return this;
-          }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.Builder builderForValue) {
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setDisconnectLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasDisconnectLog = true;
-            result.disconnectLog_ = value;
-            return this;
-          }
-
-          public Builder setDisconnectLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.Builder builderForValue) {
-            result.hasDisconnectLog = true;
-            result.disconnectLog_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setRequestType(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType value) {
+          public Builder setRequestType(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType value) {
             if (value == null) {
               throw new NullPointerException();
             }
@@ -4860,1962 +4613,1209 @@
             result.requestType_ = value;
             return this;
           }
-
-          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest internalGetResult() {
-            return result;
+          public Builder clearRequestType() {
+            result.hasRequestType = false;
+            result.requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
+            return this;
           }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest buildParsed()
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            if (!isInitialized()) {
-              throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.CapabilityExchange capabilityExchange = 2;
+          public boolean hasCapabilityExchange() {
+            return result.hasCapabilityExchange();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange getCapabilityExchange() {
+            return result.getCapabilityExchange();
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange value) {
+            if (value == null) {
+              throw new NullPointerException();
             }
-            return buildPartial();
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = value;
+            return this;
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.Builder builderForValue) {
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange value) {
+            if (result.hasCapabilityExchange() &&
+                result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance()) {
+              result.capabilityExchange_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.newBuilder(result.capabilityExchange_).mergeFrom(value).buildPartial();
+            } else {
+              result.capabilityExchange_ = value;
+            }
+            result.hasCapabilityExchange = true;
+            return this;
+          }
+          public Builder clearCapabilityExchange() {
+            result.hasCapabilityExchange = false;
+            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog addLog = 3;
+          public boolean hasAddLog() {
+            return result.hasAddLog();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog getAddLog() {
+            return result.getAddLog();
+          }
+          public Builder setAddLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasAddLog = true;
+            result.addLog_ = value;
+            return this;
+          }
+          public Builder setAddLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.Builder builderForValue) {
+            result.hasAddLog = true;
+            result.addLog_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeAddLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog value) {
+            if (result.hasAddLog() &&
+                result.addLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance()) {
+              result.addLog_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.newBuilder(result.addLog_).mergeFrom(value).buildPartial();
+            } else {
+              result.addLog_ = value;
+            }
+            result.hasAddLog = true;
+            return this;
+          }
+          public Builder clearAddLog() {
+            result.hasAddLog = false;
+            result.addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogBranch addLogBranch = 4;
+          public boolean hasAddLogBranch() {
+            return result.hasAddLogBranch();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch getAddLogBranch() {
+            return result.getAddLogBranch();
+          }
+          public Builder setAddLogBranch(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasAddLogBranch = true;
+            result.addLogBranch_ = value;
+            return this;
+          }
+          public Builder setAddLogBranch(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.Builder builderForValue) {
+            result.hasAddLogBranch = true;
+            result.addLogBranch_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeAddLogBranch(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch value) {
+            if (result.hasAddLogBranch() &&
+                result.addLogBranch_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance()) {
+              result.addLogBranch_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.newBuilder(result.addLogBranch_).mergeFrom(value).buildPartial();
+            } else {
+              result.addLogBranch_ = value;
+            }
+            result.hasAddLogBranch = true;
+            return this;
+          }
+          public Builder clearAddLogBranch() {
+            result.hasAddLogBranch = false;
+            result.addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogEntry addLogEntry = 5;
+          public boolean hasAddLogEntry() {
+            return result.hasAddLogEntry();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry getAddLogEntry() {
+            return result.getAddLogEntry();
+          }
+          public Builder setAddLogEntry(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasAddLogEntry = true;
+            result.addLogEntry_ = value;
+            return this;
+          }
+          public Builder setAddLogEntry(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.Builder builderForValue) {
+            result.hasAddLogEntry = true;
+            result.addLogEntry_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeAddLogEntry(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry value) {
+            if (result.hasAddLogEntry() &&
+                result.addLogEntry_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance()) {
+              result.addLogEntry_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.newBuilder(result.addLogEntry_).mergeFrom(value).buildPartial();
+            } else {
+              result.addLogEntry_ = value;
+            }
+            result.hasAddLogEntry = true;
+            return this;
+          }
+          public Builder clearAddLogEntry() {
+            result.hasAddLogEntry = false;
+            result.addLogEntry_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.DisconnectLog disconnectLog = 6;
+          public boolean hasDisconnectLog() {
+            return result.hasDisconnectLog();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog getDisconnectLog() {
+            return result.getDisconnectLog();
+          }
+          public Builder setDisconnectLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasDisconnectLog = true;
+            result.disconnectLog_ = value;
+            return this;
+          }
+          public Builder setDisconnectLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.Builder builderForValue) {
+            result.hasDisconnectLog = true;
+            result.disconnectLog_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeDisconnectLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog value) {
+            if (result.hasDisconnectLog() &&
+                result.disconnectLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance()) {
+              result.disconnectLog_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.newBuilder(result.disconnectLog_).mergeFrom(value).buildPartial();
+            } else {
+              result.disconnectLog_ = value;
+            }
+            result.hasDisconnectLog = true;
+            return this;
+          }
+          public Builder clearDisconnectLog() {
+            result.hasDisconnectLog = false;
+            result.disconnectLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.Initialize initialize = 7;
+          public boolean hasInitialize() {
+            return result.hasInitialize();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize getInitialize() {
+            return result.getInitialize();
+          }
+          public Builder setInitialize(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasInitialize = true;
+            result.initialize_ = value;
+            return this;
+          }
+          public Builder setInitialize(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.Builder builderForValue) {
+            result.hasInitialize = true;
+            result.initialize_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeInitialize(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize value) {
+            if (result.hasInitialize() &&
+                result.initialize_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.getDefaultInstance()) {
+              result.initialize_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.newBuilder(result.initialize_).mergeFrom(value).buildPartial();
+            } else {
+              result.initialize_ = value;
+            }
+            result.hasInitialize = true;
+            return this;
+          }
+          public Builder clearInitialize() {
+            result.hasInitialize = false;
+            result.initialize_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.getDefaultInstance();
+            return this;
           }
         }
-
-        public static final class CapabilityExchange extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
-          public static final class Builder extends
-              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-            private static Builder create() {
-              Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange();
-              return builder;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.newBuilder()
-            private Builder() {
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange build() {
-              if (result != null && !isInitialized()) {
-                throw newUninitializedMessageException(result);
-              }
-              return buildPartial();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange buildPartial() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
-              }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange returnMe = result;
-              result = null;
-              return returnMe;
-            }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
-              }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange();
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDescriptor();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-              while (true) {
-                int tag = input.readTag();
-                switch (tag) {
-                  case 0:
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  default: {
-                    if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    }
-                    break;
-                  }
-                }
-              }
-            }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance())
-                return this;
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
-            }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
-            }
-
-          }
-
-          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static CapabilityExchange getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private int memoizedSerializedSize = -1;
-
-          // Use CapabilityExchange.newBuilder() to construct.
-          private CapabilityExchange() {
-          }
-
-          public CapabilityExchange getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public final boolean isInitialized() {
-            return true;
-          }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            getUnknownFields().writeTo(output);
-          }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_fieldAccessorTable;
-          }
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
         }
-
-        public static final class DisconnectLog extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
-          public static final class Builder extends
-              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-            private static Builder create() {
-              Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog();
-              return builder;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.newBuilder()
-            private Builder() {
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog build() {
-              if (result != null && !isInitialized()) {
-                throw newUninitializedMessageException(result);
-              }
-              return buildPartial();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog buildPartial() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
-              }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog returnMe = result;
-              result = null;
-              return returnMe;
-            }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
-              }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog();
-              return this;
-            }
-
-            public Builder clearLogHandle() {
-              result.hasLogHandle = false;
-              result.logHandle_ = 0;
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDescriptor();
-            }
-
-            public int getLogHandle() {
-              return result.getLogHandle();
-            }
-
-            // required uint32 logHandle = 1;
-            public boolean hasLogHandle() {
-              return result.hasLogHandle();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-              while (true) {
-                int tag = input.readTag();
-                switch (tag) {
-                  case 0:
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  default: {
-                    if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    }
-                    break;
-                  }
-                  case 8: {
-                    setLogHandle(input.readUInt32());
-                    break;
-                  }
-                }
-              }
-            }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance())
-                return this;
-              if (other.hasLogHandle()) {
-                setLogHandle(other.getLogHandle());
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
-            }
-
-            public Builder setLogHandle(int value) {
-              result.hasLogHandle = true;
-              result.logHandle_ = value;
-              return this;
-            }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
-            }
-          }
-
-          private static final DisconnectLog defaultInstance = new DisconnectLog();
-          // required uint32 logHandle = 1;
-          public static final int LOGHANDLE_FIELD_NUMBER = 1;
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static DisconnectLog getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private boolean hasLogHandle;
-          private int logHandle_ = 0;
-          private int memoizedSerializedSize = -1;
-
-          // Use DisconnectLog.newBuilder() to construct.
-          private DisconnectLog() {
-          }
-
-          public DisconnectLog getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getLogHandle() {
-            return logHandle_;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            if (hasLogHandle()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-                  1, getLogHandle());
-            }
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public boolean hasLogHandle() {
-            return hasLogHandle;
-          }
-
-          public final boolean isInitialized() {
-            if (!hasLogHandle)
-              return false;
-            return true;
-          }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            if (hasLogHandle()) {
-              output.writeUInt32(1, getLogHandle());
-            }
-            getUnknownFields().writeTo(output);
-          }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_fieldAccessorTable;
-          }
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
         }
-
-        public static final class LogData extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
-          public static final class Builder extends
-              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-            private static Builder create() {
-              Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData();
-              return builder;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.newBuilder()
-            private Builder() {
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData build() {
-              if (result != null && !isInitialized()) {
-                throw newUninitializedMessageException(result);
-              }
-              return buildPartial();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData buildPartial() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
-              }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData returnMe = result;
-              result = null;
-              return returnMe;
-            }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
-              }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData();
-              return this;
-            }
-
-            public Builder clearDetails() {
-              result.hasDetails = false;
-              result.details_ = getDefaultInstance().getDetails();
-              return this;
-            }
-
-            public Builder clearHelpInfo() {
-              result.hasHelpInfo = false;
-              result.helpInfo_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance();
-              return this;
-            }
-
-            public Builder clearLevel() {
-              result.hasLevel = false;
-              result.level_ = getDefaultInstance().getLevel();
-              return this;
-            }
-
-            public Builder clearSummary() {
-              result.hasSummary = false;
-              result.summary_ = getDefaultInstance().getSummary();
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDescriptor();
-            }
-
-            public java.lang.String getDetails() {
-              return result.getDetails();
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo getHelpInfo() {
-              return result.getHelpInfo();
-            }
-
-            public java.lang.String getLevel() {
-              return result.getLevel();
-            }
-
-            public java.lang.String getSummary() {
-              return result.getSummary();
-            }
-
-            // optional string details = 3;
-            public boolean hasDetails() {
-              return result.hasDetails();
-            }
-
-            // optional
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData.HelpInfo
-            // helpInfo = 4;
-            public boolean hasHelpInfo() {
-              return result.hasHelpInfo();
-            }
-
-            // optional string level = 2;
-            public boolean hasLevel() {
-              return result.hasLevel();
-            }
-
-            // required string summary = 1;
-            public boolean hasSummary() {
-              return result.hasSummary();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-              while (true) {
-                int tag = input.readTag();
-                switch (tag) {
-                  case 0:
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  default: {
-                    if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    }
-                    break;
-                  }
-                  case 10: {
-                    setSummary(input.readString());
-                    break;
-                  }
-                  case 18: {
-                    setLevel(input.readString());
-                    break;
-                  }
-                  case 26: {
-                    setDetails(input.readString());
-                    break;
-                  }
-                  case 34: {
-                    com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.newBuilder();
-                    if (hasHelpInfo()) {
-                      subBuilder.mergeFrom(getHelpInfo());
-                    }
-                    input.readMessage(subBuilder, extensionRegistry);
-                    setHelpInfo(subBuilder.buildPartial());
-                    break;
-                  }
-                }
-              }
-            }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
-            }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.getDefaultInstance())
-                return this;
-              if (other.hasSummary()) {
-                setSummary(other.getSummary());
-              }
-              if (other.hasLevel()) {
-                setLevel(other.getLevel());
-              }
-              if (other.hasDetails()) {
-                setDetails(other.getDetails());
-              }
-              if (other.hasHelpInfo()) {
-                mergeHelpInfo(other.getHelpInfo());
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
-            }
-
-            public Builder mergeHelpInfo(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo value) {
-              if (result.hasHelpInfo()
-                  && result.helpInfo_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance()) {
-                result.helpInfo_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.newBuilder(
-                    result.helpInfo_).mergeFrom(value).buildPartial();
-              } else {
-                result.helpInfo_ = value;
-              }
-              result.hasHelpInfo = true;
-              return this;
-            }
-
-            public Builder setDetails(java.lang.String value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.hasDetails = true;
-              result.details_ = value;
-              return this;
-            }
-
-            public Builder setHelpInfo(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.hasHelpInfo = true;
-              result.helpInfo_ = value;
-              return this;
-            }
-
-            public Builder setHelpInfo(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.Builder builderForValue) {
-              result.hasHelpInfo = true;
-              result.helpInfo_ = builderForValue.build();
-              return this;
-            }
-
-            public Builder setLevel(java.lang.String value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.hasLevel = true;
-              result.level_ = value;
-              return this;
-            }
-
-            public Builder setSummary(java.lang.String value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.hasSummary = true;
-              result.summary_ = value;
-              return this;
-            }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
-            }
-          }
-
-          public static final class HelpInfo extends
-              com.google.gwt.dev.protobuf.GeneratedMessage {
-            public static final class Builder extends
-                com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-              private static Builder create() {
-                Builder builder = new Builder();
-                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo();
-                return builder;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo result;
-
-              // Construct using
-              // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.newBuilder()
-              private Builder() {
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo build() {
-                if (result != null && !isInitialized()) {
-                  throw newUninitializedMessageException(result);
-                }
-                return buildPartial();
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo buildPartial() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "build() has already been called on this Builder.");
-                }
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo returnMe = result;
-                result = null;
-                return returnMe;
-              }
-
-              public Builder clear() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "Cannot call clear() after build().");
-                }
-                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo();
-                return this;
-              }
-
-              public Builder clearText() {
-                result.hasText = false;
-                result.text_ = getDefaultInstance().getText();
-                return this;
-              }
-
-              public Builder clearUrl() {
-                result.hasUrl = false;
-                result.url_ = getDefaultInstance().getUrl();
-                return this;
-              }
-
-              public Builder clone() {
-                return create().mergeFrom(result);
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo getDefaultInstanceForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance();
-              }
-
-              public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDescriptor();
-              }
-
-              public java.lang.String getText() {
-                return result.getText();
-              }
-
-              public java.lang.String getUrl() {
-                return result.getUrl();
-              }
-
-              // optional string text = 2;
-              public boolean hasText() {
-                return result.hasText();
-              }
-
-              // optional string url = 1;
-              public boolean hasUrl() {
-                return result.hasUrl();
-              }
-
-              public boolean isInitialized() {
-                return result.isInitialized();
-              }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.protobuf.CodedInputStream input,
-                  com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                  throws java.io.IOException {
-                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-                while (true) {
-                  int tag = input.readTag();
-                  switch (tag) {
-                    case 0:
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    default: {
-                      if (!parseUnknownField(input, unknownFields,
-                          extensionRegistry, tag)) {
-                        this.setUnknownFields(unknownFields.build());
-                        return this;
-                      }
-                      break;
-                    }
-                    case 10: {
-                      setUrl(input.readString());
-                      break;
-                    }
-                    case 18: {
-                      setText(input.readString());
-                      break;
-                    }
-                  }
-                }
-              }
-
-              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo) {
-                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo) other);
-                } else {
-                  super.mergeFrom(other);
-                  return this;
-                }
-              }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo other) {
-                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance())
-                  return this;
-                if (other.hasUrl()) {
-                  setUrl(other.getUrl());
-                }
-                if (other.hasText()) {
-                  setText(other.getText());
-                }
-                this.mergeUnknownFields(other.getUnknownFields());
-                return this;
-              }
-
-              public Builder setText(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasText = true;
-                result.text_ = value;
-                return this;
-              }
-
-              public Builder setUrl(java.lang.String value) {
-                if (value == null) {
-                  throw new NullPointerException();
-                }
-                result.hasUrl = true;
-                result.url_ = value;
-                return this;
-              }
-
-              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo internalGetResult() {
-                return result;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo buildParsed()
-                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-                if (!isInitialized()) {
-                  throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-                }
-                return buildPartial();
-              }
-            }
-
-            private static final HelpInfo defaultInstance = new HelpInfo();
-            // optional string url = 1;
-            public static final int URL_FIELD_NUMBER = 1;
-
-            // optional string text = 2;
-            public static final int TEXT_FIELD_NUMBER = 2;
-
-            static {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-            }
-
-            static {
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-            }
-
-            public static HelpInfo getDefaultInstance() {
-              return defaultInstance;
-            }
-
-            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor;
-            }
-
-            public static Builder newBuilder() {
-              return Builder.create();
-            }
-
-            public static Builder newBuilder(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo prototype) {
-              return newBuilder().mergeFrom(prototype);
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseDelimitedFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseDelimitedFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                byte[] data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                byte[] data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo parseFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            private boolean hasUrl;
-            private java.lang.String url_ = "";
-            private boolean hasText;
-            private java.lang.String text_ = "";
-            private int memoizedSerializedSize = -1;
-
-            // Use HelpInfo.newBuilder() to construct.
-            private HelpInfo() {
-            }
-
-            public HelpInfo getDefaultInstanceForType() {
-              return defaultInstance;
-            }
-
-            public int getSerializedSize() {
-              int size = memoizedSerializedSize;
-              if (size != -1)
-                return size;
-
-              size = 0;
-              if (hasUrl()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    1, getUrl());
-              }
-              if (hasText()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                    2, getText());
-              }
-              size += getUnknownFields().getSerializedSize();
-              memoizedSerializedSize = size;
-              return size;
-            }
-
-            public java.lang.String getText() {
-              return text_;
-            }
-
-            public java.lang.String getUrl() {
-              return url_;
-            }
-
-            public boolean hasText() {
-              return hasText;
-            }
-
-            public boolean hasUrl() {
-              return hasUrl;
-            }
-
-            public final boolean isInitialized() {
-              return true;
-            }
-
-            public Builder newBuilderForType() {
-              return newBuilder();
-            }
-
-            public Builder toBuilder() {
-              return newBuilder(this);
-            }
-
-            public void writeTo(
-                com.google.gwt.dev.protobuf.CodedOutputStream output)
-                throws java.io.IOException {
-              if (hasUrl()) {
-                output.writeString(1, getUrl());
-              }
-              if (hasText()) {
-                output.writeString(2, getText());
-              }
-              getUnknownFields().writeTo(output);
-            }
-
-            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_fieldAccessorTable;
-            }
-          }
-
-          private static final LogData defaultInstance = new LogData();
-
-          // required string summary = 1;
-          public static final int SUMMARY_FIELD_NUMBER = 1;
-
-          // optional string level = 2;
-          public static final int LEVEL_FIELD_NUMBER = 2;
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static LogData getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private boolean hasSummary;
-
-          private java.lang.String summary_ = "";
-          private boolean hasLevel;
-          private java.lang.String level_ = "";
-          // optional string details = 3;
-          public static final int DETAILS_FIELD_NUMBER = 3;
-          private boolean hasDetails;
-
-          private java.lang.String details_ = "";
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.LogData.HelpInfo
-          // helpInfo = 4;
-          public static final int HELPINFO_FIELD_NUMBER = 4;
-
-          private boolean hasHelpInfo;
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo helpInfo_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.getDefaultInstance();
-
-          private int memoizedSerializedSize = -1;
-
-          // Use LogData.newBuilder() to construct.
-          private LogData() {
-          }
-
-          public LogData getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public java.lang.String getDetails() {
-            return details_;
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo getHelpInfo() {
-            return helpInfo_;
-          }
-
-          public java.lang.String getLevel() {
-            return level_;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            if (hasSummary()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                  1, getSummary());
-            }
-            if (hasLevel()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                  2, getLevel());
-            }
-            if (hasDetails()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeStringSize(
-                  3, getDetails());
-            }
-            if (hasHelpInfo()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  4, getHelpInfo());
-            }
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public java.lang.String getSummary() {
-            return summary_;
-          }
-
-          public boolean hasDetails() {
-            return hasDetails;
-          }
-
-          public boolean hasHelpInfo() {
-            return hasHelpInfo;
-          }
-
-          public boolean hasLevel() {
-            return hasLevel;
-          }
-
-          public boolean hasSummary() {
-            return hasSummary;
-          }
-
-          public final boolean isInitialized() {
-            if (!hasSummary)
-              return false;
-            return true;
-          }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            if (hasSummary()) {
-              output.writeString(1, getSummary());
-            }
-            if (hasLevel()) {
-              output.writeString(2, getLevel());
-            }
-            if (hasDetails()) {
-              output.writeString(3, getDetails());
-            }
-            if (hasHelpInfo()) {
-              output.writeMessage(4, getHelpInfo());
-            }
-            getUnknownFields().writeTo(output);
-          }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_fieldAccessorTable;
-          }
+      }
+      
+      public static final class DevModeRequest extends
+          com.google.gwt.dev.protobuf.GeneratedMessage {
+        // Use DevModeRequest.newBuilder() to construct.
+        private DevModeRequest() {}
+        
+        private static final DevModeRequest defaultInstance = new DevModeRequest();
+        public static DevModeRequest getDefaultInstance() {
+          return defaultInstance;
         }
-
-        public enum RequestType implements
-            com.google.gwt.dev.protobuf.ProtocolMessageEnum {
-          CAPABILITY_EXCHANGE(0, 0), ADD_LOG(1, 1), ADD_LOG_BRANCH(2, 2), ADD_LOG_ENTRY(
-              3, 3), DISCONNECT_LOG(4, 4), ;
-
-          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType> internalValueMap = new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>() {
-            public RequestType findValueByNumber(int number) {
-              return RequestType.valueOf(number);
+        
+        public DevModeRequest getDefaultInstanceForType() {
+          return defaultInstance;
+        }
+        
+        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+            getDescriptor() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor;
+        }
+        
+        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+            internalGetFieldAccessorTable() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_fieldAccessorTable;
+        }
+        
+        public enum RequestType
+            implements com.google.gwt.dev.protobuf.ProtocolMessageEnum {
+          CAPABILITY_EXCHANGE(0, 0),
+          RESTART_WEB_SERVER(1, 1),
+          ;
+          
+          
+          public final int getNumber() { return value; }
+          
+          public static RequestType valueOf(int value) {
+            switch (value) {
+              case 0: return CAPABILITY_EXCHANGE;
+              case 1: return RESTART_WEB_SERVER;
+              default: return null;
             }
-          };
-
-          private static final RequestType[] VALUES = {
-              CAPABILITY_EXCHANGE, ADD_LOG, ADD_LOG_BRANCH, ADD_LOG_ENTRY,
-              DISCONNECT_LOG,};
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDescriptor().getEnumTypes().get(
-                0);
           }
-
-          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType> internalGetValueMap() {
+          
+          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>
+              internalGetValueMap() {
             return internalValueMap;
           }
-
+          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>
+              internalValueMap =
+                new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<RequestType>() {
+                  public RequestType findValueByNumber(int number) {
+                    return RequestType.valueOf(number)
+          ;        }
+                };
+          
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor
+              getValueDescriptor() {
+            return getDescriptor().getValues().get(index);
+          }
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptorForType() {
+            return getDescriptor();
+          }
+          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDescriptor().getEnumTypes().get(0);
+          }
+          
+          private static final RequestType[] VALUES = {
+            CAPABILITY_EXCHANGE, RESTART_WEB_SERVER, 
+          };
           public static RequestType valueOf(
               com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
             if (desc.getType() != getDescriptor()) {
               throw new java.lang.IllegalArgumentException(
-                  "EnumValueDescriptor is not for this type.");
+                "EnumValueDescriptor is not for this type.");
             }
             return VALUES[desc.getIndex()];
           }
-
-          public static RequestType valueOf(int value) {
-            switch (value) {
-              case 0:
-                return CAPABILITY_EXCHANGE;
-              case 1:
-                return ADD_LOG;
-              case 2:
-                return ADD_LOG_BRANCH;
-              case 3:
-                return ADD_LOG_ENTRY;
-              case 4:
-                return DISCONNECT_LOG;
-              default:
-                return null;
-            }
-          }
-
           private final int index;
-
           private final int value;
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
           private RequestType(int index, int value) {
             this.index = index;
             this.value = value;
           }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptorForType() {
-            return getDescriptor();
-          }
-
-          public final int getNumber() {
-            return value;
-          }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() {
-            return getDescriptor().getValues().get(index);
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
         }
-
-        private static final ViewerRequest defaultInstance = new ViewerRequest();
-
-        // required
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType
-        // requestType = 1;
-        public static final int REQUESTTYPE_FIELD_NUMBER = 1;
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.CapabilityExchange
-        // capabilityExchange = 2;
-        public static final int CAPABILITYEXCHANGE_FIELD_NUMBER = 2;
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogEntry
-        // addLogEntry = 5;
-        public static final int ADDLOGENTRY_FIELD_NUMBER = 5;
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-        }
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-        }
-
-        public static ViewerRequest getDefaultInstance() {
-          return defaultInstance;
-        }
-
-        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor;
-        }
-
-        public static Builder newBuilder() {
-          return Builder.create();
-        }
-
-        public static Builder newBuilder(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest prototype) {
-          return newBuilder().mergeFrom(prototype);
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseDelimitedFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseDelimitedFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            byte[] data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            byte[] data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest parseFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
-        private boolean hasRequestType;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
-        private boolean hasCapabilityExchange;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.getDefaultInstance();
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLog
-        // addLog = 3;
-        public static final int ADDLOG_FIELD_NUMBER = 3;
-
-        private boolean hasAddLog;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.getDefaultInstance();
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.AddLogBranch
-        // addLogBranch = 4;
-        public static final int ADDLOGBRANCH_FIELD_NUMBER = 4;
-        private boolean hasAddLogBranch;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.getDefaultInstance();
-
-        private boolean hasAddLogEntry;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry addLogEntry_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.getDefaultInstance();
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.DisconnectLog
-        // disconnectLog = 6;
-        public static final int DISCONNECTLOG_FIELD_NUMBER = 6;
-        private boolean hasDisconnectLog;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog disconnectLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.getDefaultInstance();
-
-        private int memoizedSerializedSize = -1;
-
-        // Use ViewerRequest.newBuilder() to construct.
-        private ViewerRequest() {
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog getAddLog() {
-          return addLog_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch getAddLogBranch() {
-          return addLogBranch_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry getAddLogEntry() {
-          return addLogEntry_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange getCapabilityExchange() {
-          return capabilityExchange_;
-        }
-
-        public ViewerRequest getDefaultInstanceForType() {
-          return defaultInstance;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog getDisconnectLog() {
-          return disconnectLog_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getRequestType() {
-          return requestType_;
-        }
-
-        public int getSerializedSize() {
-          int size = memoizedSerializedSize;
-          if (size != -1)
+        
+        public static final class CapabilityExchange extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use CapabilityExchange.newBuilder() to construct.
+          private CapabilityExchange() {}
+          
+          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
+          public static CapabilityExchange getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public CapabilityExchange getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_fieldAccessorTable;
+          }
+          
+          public final boolean isInitialized() {
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
             return size;
-
-          size = 0;
-          if (hasRequestType()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-                1, getRequestType().getNumber());
           }
-          if (hasCapabilityExchange()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                2, getCapabilityExchange());
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-          if (hasAddLog()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                3, getAddLog());
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-          if (hasAddLogBranch()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                4, getAddLogBranch());
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-          if (hasAddLogEntry()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                5, getAddLogEntry());
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-          if (hasDisconnectLog()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                6, getDisconnectLog());
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
           }
-          size += getUnknownFields().getSerializedSize();
-          memoizedSerializedSize = size;
-          return size;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange();
+              return builder;
+            }
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange internalGetResult() {
+              return result;
+            }
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance()) return this;
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                }
+              }
+            }
+            
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+          }
         }
-
-        public boolean hasAddLog() {
-          return hasAddLog;
+        
+        public static final class RestartWebServer extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use RestartWebServer.newBuilder() to construct.
+          private RestartWebServer() {}
+          
+          private static final RestartWebServer defaultInstance = new RestartWebServer();
+          public static RestartWebServer getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public RestartWebServer getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_fieldAccessorTable;
+          }
+          
+          public final boolean isInitialized() {
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
+          }
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer();
+              return builder;
+            }
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer internalGetResult() {
+              return result;
+            }
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance()) return this;
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                }
+              }
+            }
+            
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+          }
         }
-
-        public boolean hasAddLogBranch() {
-          return hasAddLogBranch;
-        }
-
-        public boolean hasAddLogEntry() {
-          return hasAddLogEntry;
-        }
-
-        public boolean hasCapabilityExchange() {
-          return hasCapabilityExchange;
-        }
-
-        public boolean hasDisconnectLog() {
-          return hasDisconnectLog;
-        }
-
-        public boolean hasRequestType() {
-          return hasRequestType;
-        }
-
+        
+        // required .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType requestType = 1;
+        public static final int REQUESTTYPE_FIELD_NUMBER = 1;
+        private boolean hasRequestType;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
+        public boolean hasRequestType() { return hasRequestType; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getRequestType() { return requestType_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.CapabilityExchange capabilityExchange = 2;
+        public static final int CAPABILITYEXCHANGE_FIELD_NUMBER = 2;
+        private boolean hasCapabilityExchange;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance();
+        public boolean hasCapabilityExchange() { return hasCapabilityExchange; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange getCapabilityExchange() { return capabilityExchange_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RestartWebServer restartWebServer = 3;
+        public static final int RESTARTWEBSERVER_FIELD_NUMBER = 3;
+        private boolean hasRestartWebServer;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance();
+        public boolean hasRestartWebServer() { return hasRestartWebServer; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer getRestartWebServer() { return restartWebServer_; }
+        
         public final boolean isInitialized() {
-          if (!hasRequestType)
-            return false;
-          if (hasAddLog()) {
-            if (!getAddLog().isInitialized())
-              return false;
-          }
-          if (hasAddLogBranch()) {
-            if (!getAddLogBranch().isInitialized())
-              return false;
-          }
-          if (hasAddLogEntry()) {
-            if (!getAddLogEntry().isInitialized())
-              return false;
-          }
-          if (hasDisconnectLog()) {
-            if (!getDisconnectLog().isInitialized())
-              return false;
-          }
+          if (!hasRequestType) return false;
           return true;
         }
-
-        public Builder newBuilderForType() {
-          return newBuilder();
-        }
-
-        public Builder toBuilder() {
-          return newBuilder(this);
-        }
-
+        
         public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
-            throws java.io.IOException {
+                            throws java.io.IOException {
           if (hasRequestType()) {
             output.writeEnum(1, getRequestType().getNumber());
           }
           if (hasCapabilityExchange()) {
             output.writeMessage(2, getCapabilityExchange());
           }
-          if (hasAddLog()) {
-            output.writeMessage(3, getAddLog());
-          }
-          if (hasAddLogBranch()) {
-            output.writeMessage(4, getAddLogBranch());
-          }
-          if (hasAddLogEntry()) {
-            output.writeMessage(5, getAddLogEntry());
-          }
-          if (hasDisconnectLog()) {
-            output.writeMessage(6, getDisconnectLog());
+          if (hasRestartWebServer()) {
+            output.writeMessage(3, getRestartWebServer());
           }
           getUnknownFields().writeTo(output);
         }
-
-        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_fieldAccessorTable;
+        
+        private int memoizedSerializedSize = -1;
+        public int getSerializedSize() {
+          int size = memoizedSerializedSize;
+          if (size != -1) return size;
+        
+          size = 0;
+          if (hasRequestType()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeEnumSize(1, getRequestType().getNumber());
+          }
+          if (hasCapabilityExchange()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(2, getCapabilityExchange());
+          }
+          if (hasRestartWebServer()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(3, getRestartWebServer());
+          }
+          size += getUnknownFields().getSerializedSize();
+          memoizedSerializedSize = size;
+          return size;
+        }
+        
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(byte[] data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
+            byte[] data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseDelimitedFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseDelimitedFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        
+        public static Builder newBuilder() { return Builder.create(); }
+        public Builder newBuilderForType() { return newBuilder(); }
+        public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest prototype) {
+          return newBuilder().mergeFrom(prototype);
+        }
+        public Builder toBuilder() { return newBuilder(this); }
+        
+        public static final class Builder extends
+            com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest result;
+          
+          // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.newBuilder()
+          private Builder() {}
+          
+          private static Builder create() {
+            Builder builder = new Builder();
+            builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest();
+            return builder;
+          }
+          
+          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest internalGetResult() {
+            return result;
+          }
+          
+          public Builder clear() {
+            if (result == null) {
+              throw new IllegalStateException(
+                "Cannot call clear() after build().");
+            }
+            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest();
+            return this;
+          }
+          
+          public Builder clone() {
+            return create().mergeFrom(result);
+          }
+          
+          public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptorForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDescriptor();
+          }
+          
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest getDefaultInstanceForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance();
+          }
+          
+          public boolean isInitialized() {
+            return result.isInitialized();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest build() {
+            if (result != null && !isInitialized()) {
+              throw newUninitializedMessageException(result);
+            }
+            return buildPartial();
+          }
+          
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest buildParsed()
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            if (!isInitialized()) {
+              throw newUninitializedMessageException(
+                result).asInvalidProtocolBufferException();
+            }
+            return buildPartial();
+          }
+          
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest buildPartial() {
+            if (result == null) {
+              throw new IllegalStateException(
+                "build() has already been called on this Builder.");
+            }
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest returnMe = result;
+            result = null;
+            return returnMe;
+          }
+          
+          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest) {
+              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest)other);
+            } else {
+              super.mergeFrom(other);
+              return this;
+            }
+          }
+          
+          public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest other) {
+            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance()) return this;
+            if (other.hasRequestType()) {
+              setRequestType(other.getRequestType());
+            }
+            if (other.hasCapabilityExchange()) {
+              mergeCapabilityExchange(other.getCapabilityExchange());
+            }
+            if (other.hasRestartWebServer()) {
+              mergeRestartWebServer(other.getRestartWebServer());
+            }
+            this.mergeUnknownFields(other.getUnknownFields());
+            return this;
+          }
+          
+          public Builder mergeFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+              com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                this.getUnknownFields());
+            while (true) {
+              int tag = input.readTag();
+              switch (tag) {
+                case 0:
+                  this.setUnknownFields(unknownFields.build());
+                  return this;
+                default: {
+                  if (!parseUnknownField(input, unknownFields,
+                                         extensionRegistry, tag)) {
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  }
+                  break;
+                }
+                case 8: {
+                  int rawValue = input.readEnum();
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.valueOf(rawValue);
+                  if (value == null) {
+                    unknownFields.mergeVarintField(1, rawValue);
+                  } else {
+                    setRequestType(value);
+                  }
+                  break;
+                }
+                case 18: {
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.newBuilder();
+                  if (hasCapabilityExchange()) {
+                    subBuilder.mergeFrom(getCapabilityExchange());
+                  }
+                  input.readMessage(subBuilder, extensionRegistry);
+                  setCapabilityExchange(subBuilder.buildPartial());
+                  break;
+                }
+                case 26: {
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.newBuilder();
+                  if (hasRestartWebServer()) {
+                    subBuilder.mergeFrom(getRestartWebServer());
+                  }
+                  input.readMessage(subBuilder, extensionRegistry);
+                  setRestartWebServer(subBuilder.buildPartial());
+                  break;
+                }
+              }
+            }
+          }
+          
+          
+          // required .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType requestType = 1;
+          public boolean hasRequestType() {
+            return result.hasRequestType();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getRequestType() {
+            return result.getRequestType();
+          }
+          public Builder setRequestType(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasRequestType = true;
+            result.requestType_ = value;
+            return this;
+          }
+          public Builder clearRequestType() {
+            result.hasRequestType = false;
+            result.requestType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.CapabilityExchange capabilityExchange = 2;
+          public boolean hasCapabilityExchange() {
+            return result.hasCapabilityExchange();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange getCapabilityExchange() {
+            return result.getCapabilityExchange();
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = value;
+            return this;
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.Builder builderForValue) {
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange value) {
+            if (result.hasCapabilityExchange() &&
+                result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance()) {
+              result.capabilityExchange_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.newBuilder(result.capabilityExchange_).mergeFrom(value).buildPartial();
+            } else {
+              result.capabilityExchange_ = value;
+            }
+            result.hasCapabilityExchange = true;
+            return this;
+          }
+          public Builder clearCapabilityExchange() {
+            result.hasCapabilityExchange = false;
+            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RestartWebServer restartWebServer = 3;
+          public boolean hasRestartWebServer() {
+            return result.hasRestartWebServer();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer getRestartWebServer() {
+            return result.getRestartWebServer();
+          }
+          public Builder setRestartWebServer(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasRestartWebServer = true;
+            result.restartWebServer_ = value;
+            return this;
+          }
+          public Builder setRestartWebServer(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.Builder builderForValue) {
+            result.hasRestartWebServer = true;
+            result.restartWebServer_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeRestartWebServer(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer value) {
+            if (result.hasRestartWebServer() &&
+                result.restartWebServer_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance()) {
+              result.restartWebServer_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.newBuilder(result.restartWebServer_).mergeFrom(value).buildPartial();
+            } else {
+              result.restartWebServer_ = value;
+            }
+            result.hasRestartWebServer = true;
+            return this;
+          }
+          public Builder clearRestartWebServer() {
+            result.hasRestartWebServer = false;
+            result.restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.getDefaultInstance();
+            return this;
+          }
+        }
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+        }
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
         }
       }
-
-      private static final Request defaultInstance = new Request();
-
-      // required .com.google.gwt.dev.shell.remoteui.Message.Request.ServiceType
-      // serviceType = 1;
+      
+      // required .com.google.gwt.dev.shell.remoteui.Message.Request.ServiceType serviceType = 1;
       public static final int SERVICETYPE_FIELD_NUMBER = 1;
-
+      private boolean hasServiceType;
+      private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType serviceType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType.VIEWER;
+      public boolean hasServiceType() { return hasServiceType; }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType getServiceType() { return serviceType_; }
+      
       // optional uint32 requestId = 2;
       public static final int REQUESTID_FIELD_NUMBER = 2;
-
-      static {
-        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-      }
-
-      static {
-        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-      }
-
-      public static Request getDefaultInstance() {
-        return defaultInstance;
-      }
-
-      public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor;
-      }
-
-      public static Builder newBuilder() {
-        return Builder.create();
-      }
-
-      public static Builder newBuilder(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request prototype) {
-        return newBuilder().mergeFrom(prototype);
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseDelimitedFrom(
-          java.io.InputStream input) throws java.io.IOException {
-        return newBuilder().mergeDelimitedFrom(input).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseDelimitedFrom(
-          java.io.InputStream input,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws java.io.IOException {
-        return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          byte[] data)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          byte[] data,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          com.google.gwt.dev.protobuf.ByteString data)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          com.google.gwt.dev.protobuf.ByteString data,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          com.google.gwt.dev.protobuf.CodedInputStream input)
-          throws java.io.IOException {
-        return newBuilder().mergeFrom(input).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          com.google.gwt.dev.protobuf.CodedInputStream input,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws java.io.IOException {
-        return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          java.io.InputStream input) throws java.io.IOException {
-        return newBuilder().mergeFrom(input).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
-          java.io.InputStream input,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws java.io.IOException {
-        return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-      }
-
-      private boolean hasServiceType;
-
-      private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType serviceType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType.VIEWER;
       private boolean hasRequestId;
       private int requestId_ = 0;
-      // optional
-      // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest
-      // viewerRequest = 3;
+      public boolean hasRequestId() { return hasRequestId; }
+      public int getRequestId() { return requestId_; }
+      
+      // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest viewerRequest = 3;
       public static final int VIEWERREQUEST_FIELD_NUMBER = 3;
       private boolean hasViewerRequest;
-
       private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest viewerRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance();
-
-      // optional
-      // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest
-      // devModeRequest = 4;
+      public boolean hasViewerRequest() { return hasViewerRequest; }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest getViewerRequest() { return viewerRequest_; }
+      
+      // optional .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest devModeRequest = 4;
       public static final int DEVMODEREQUEST_FIELD_NUMBER = 4;
-
       private boolean hasDevModeRequest;
       private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest devModeRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance();
-
-      private int memoizedSerializedSize = -1;
-
-      // Use Request.newBuilder() to construct.
-      private Request() {
-      }
-
-      public Request getDefaultInstanceForType() {
-        return defaultInstance;
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest getDevModeRequest() {
-        return devModeRequest_;
-      }
-
-      public int getRequestId() {
-        return requestId_;
-      }
-
-      public int getSerializedSize() {
-        int size = memoizedSerializedSize;
-        if (size != -1)
-          return size;
-
-        size = 0;
-        if (hasServiceType()) {
-          size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-              1, getServiceType().getNumber());
-        }
-        if (hasRequestId()) {
-          size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-              2, getRequestId());
-        }
-        if (hasViewerRequest()) {
-          size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-              3, getViewerRequest());
-        }
-        if (hasDevModeRequest()) {
-          size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-              4, getDevModeRequest());
-        }
-        size += getUnknownFields().getSerializedSize();
-        memoizedSerializedSize = size;
-        return size;
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType getServiceType() {
-        return serviceType_;
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest getViewerRequest() {
-        return viewerRequest_;
-      }
-
-      public boolean hasDevModeRequest() {
-        return hasDevModeRequest;
-      }
-
-      public boolean hasRequestId() {
-        return hasRequestId;
-      }
-
-      public boolean hasServiceType() {
-        return hasServiceType;
-      }
-
-      public boolean hasViewerRequest() {
-        return hasViewerRequest;
-      }
-
+      public boolean hasDevModeRequest() { return hasDevModeRequest; }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest getDevModeRequest() { return devModeRequest_; }
+      
       public final boolean isInitialized() {
-        if (!hasServiceType)
-          return false;
+        if (!hasServiceType) return false;
         if (hasViewerRequest()) {
-          if (!getViewerRequest().isInitialized())
-            return false;
+          if (!getViewerRequest().isInitialized()) return false;
         }
         if (hasDevModeRequest()) {
-          if (!getDevModeRequest().isInitialized())
-            return false;
+          if (!getDevModeRequest().isInitialized()) return false;
         }
         return true;
       }
-
-      public Builder newBuilderForType() {
-        return newBuilder();
-      }
-
-      public Builder toBuilder() {
-        return newBuilder(this);
-      }
-
+      
       public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
-          throws java.io.IOException {
+                          throws java.io.IOException {
         if (hasServiceType()) {
           output.writeEnum(1, getServiceType().getNumber());
         }
@@ -6830,138 +5830,201 @@
         }
         getUnknownFields().writeTo(output);
       }
-
-      protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_fieldAccessorTable;
+      
+      private int memoizedSerializedSize = -1;
+      public int getSerializedSize() {
+        int size = memoizedSerializedSize;
+        if (size != -1) return size;
+      
+        size = 0;
+        if (hasServiceType()) {
+          size += com.google.gwt.dev.protobuf.CodedOutputStream
+            .computeEnumSize(1, getServiceType().getNumber());
+        }
+        if (hasRequestId()) {
+          size += com.google.gwt.dev.protobuf.CodedOutputStream
+            .computeUInt32Size(2, getRequestId());
+        }
+        if (hasViewerRequest()) {
+          size += com.google.gwt.dev.protobuf.CodedOutputStream
+            .computeMessageSize(3, getViewerRequest());
+        }
+        if (hasDevModeRequest()) {
+          size += com.google.gwt.dev.protobuf.CodedOutputStream
+            .computeMessageSize(4, getDevModeRequest());
+        }
+        size += getUnknownFields().getSerializedSize();
+        memoizedSerializedSize = size;
+        return size;
       }
-    }
-
-    public static final class Response extends
-        com.google.gwt.dev.protobuf.GeneratedMessage {
+      
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
+          com.google.gwt.dev.protobuf.ByteString data)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
+          com.google.gwt.dev.protobuf.ByteString data,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(byte[] data)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
+          byte[] data,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(java.io.InputStream input)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
+          java.io.InputStream input,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseDelimitedFrom(java.io.InputStream input)
+          throws java.io.IOException {
+        return newBuilder().mergeDelimitedFrom(input).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseDelimitedFrom(
+          java.io.InputStream input,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws java.io.IOException {
+        return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
+          com.google.gwt.dev.protobuf.CodedInputStream input)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request parseFrom(
+          com.google.gwt.dev.protobuf.CodedInputStream input,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input, extensionRegistry)
+                 .buildParsed();
+      }
+      
+      public static Builder newBuilder() { return Builder.create(); }
+      public Builder newBuilderForType() { return newBuilder(); }
+      public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request prototype) {
+        return newBuilder().mergeFrom(prototype);
+      }
+      public Builder toBuilder() { return newBuilder(this); }
+      
       public static final class Builder extends
           com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request result;
+        
+        // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.newBuilder()
+        private Builder() {}
+        
         private static Builder create() {
           Builder builder = new Builder();
-          builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response();
+          builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request();
           return builder;
         }
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response result;
-
-        // Construct using
-        // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.newBuilder()
-        private Builder() {
+        
+        protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request internalGetResult() {
+          return result;
         }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response build() {
+        
+        public Builder clear() {
+          if (result == null) {
+            throw new IllegalStateException(
+              "Cannot call clear() after build().");
+          }
+          result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request();
+          return this;
+        }
+        
+        public Builder clone() {
+          return create().mergeFrom(result);
+        }
+        
+        public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+            getDescriptorForType() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDescriptor();
+        }
+        
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request getDefaultInstanceForType() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance();
+        }
+        
+        public boolean isInitialized() {
+          return result.isInitialized();
+        }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request build() {
           if (result != null && !isInitialized()) {
             throw newUninitializedMessageException(result);
           }
           return buildPartial();
         }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response buildPartial() {
+        
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request buildParsed()
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          if (!isInitialized()) {
+            throw newUninitializedMessageException(
+              result).asInvalidProtocolBufferException();
+          }
+          return buildPartial();
+        }
+        
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request buildPartial() {
           if (result == null) {
             throw new IllegalStateException(
-                "build() has already been called on this Builder.");
+              "build() has already been called on this Builder.");
           }
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response returnMe = result;
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request returnMe = result;
           result = null;
           return returnMe;
         }
-
-        public Builder clear() {
-          if (result == null) {
-            throw new IllegalStateException(
-                "Cannot call clear() after build().");
-          }
-          result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response();
-          return this;
-        }
-
-        public Builder clearDevModeResponse() {
-          result.hasDevModeResponse = false;
-          result.devModeResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance();
-          return this;
-        }
-
-        public Builder clearRequestId() {
-          result.hasRequestId = false;
-          result.requestId_ = 0;
-          return this;
-        }
-
-        public Builder clearViewerResponse() {
-          result.hasViewerResponse = false;
-          result.viewerResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance();
-          return this;
-        }
-
-        public Builder clone() {
-          return create().mergeFrom(result);
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response getDefaultInstanceForType() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance();
-        }
-
-        public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDescriptor();
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse getDevModeResponse() {
-          return result.getDevModeResponse();
-        }
-
-        public int getRequestId() {
-          return result.getRequestId();
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse getViewerResponse() {
-          return result.getViewerResponse();
-        }
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse
-        // devModeResponse = 3;
-        public boolean hasDevModeResponse() {
-          return result.hasDevModeResponse();
-        }
-
-        // required uint32 requestId = 1;
-        public boolean hasRequestId() {
-          return result.hasRequestId();
-        }
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse
-        // viewerResponse = 2;
-        public boolean hasViewerResponse() {
-          return result.hasViewerResponse();
-        }
-
-        public boolean isInitialized() {
-          return result.isInitialized();
-        }
-
-        public Builder mergeDevModeResponse(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse value) {
-          if (result.hasDevModeResponse()
-              && result.devModeResponse_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance()) {
-            result.devModeResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.newBuilder(
-                result.devModeResponse_).mergeFrom(value).buildPartial();
+        
+        public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+          if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request) {
+            return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request)other);
           } else {
-            result.devModeResponse_ = value;
+            super.mergeFrom(other);
+            return this;
           }
-          result.hasDevModeResponse = true;
+        }
+        
+        public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request other) {
+          if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance()) return this;
+          if (other.hasServiceType()) {
+            setServiceType(other.getServiceType());
+          }
+          if (other.hasRequestId()) {
+            setRequestId(other.getRequestId());
+          }
+          if (other.hasViewerRequest()) {
+            mergeViewerRequest(other.getViewerRequest());
+          }
+          if (other.hasDevModeRequest()) {
+            mergeDevModeRequest(other.getDevModeRequest());
+          }
+          this.mergeUnknownFields(other.getUnknownFields());
           return this;
         }
-
+        
         public Builder mergeFrom(
             com.google.gwt.dev.protobuf.CodedInputStream input,
             com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
             throws java.io.IOException {
-          com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+          com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+            com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+              this.getUnknownFields());
           while (true) {
             int tag = input.readTag();
             switch (tag) {
@@ -6969,677 +6032,529 @@
                 this.setUnknownFields(unknownFields.build());
                 return this;
               default: {
-                if (!parseUnknownField(input, unknownFields, extensionRegistry,
-                    tag)) {
+                if (!parseUnknownField(input, unknownFields,
+                                       extensionRegistry, tag)) {
                   this.setUnknownFields(unknownFields.build());
                   return this;
                 }
                 break;
               }
               case 8: {
+                int rawValue = input.readEnum();
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType.valueOf(rawValue);
+                if (value == null) {
+                  unknownFields.mergeVarintField(1, rawValue);
+                } else {
+                  setServiceType(value);
+                }
+                break;
+              }
+              case 16: {
                 setRequestId(input.readUInt32());
                 break;
               }
-              case 18: {
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.newBuilder();
-                if (hasViewerResponse()) {
-                  subBuilder.mergeFrom(getViewerResponse());
+              case 26: {
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.newBuilder();
+                if (hasViewerRequest()) {
+                  subBuilder.mergeFrom(getViewerRequest());
                 }
                 input.readMessage(subBuilder, extensionRegistry);
-                setViewerResponse(subBuilder.buildPartial());
+                setViewerRequest(subBuilder.buildPartial());
                 break;
               }
-              case 26: {
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.newBuilder();
-                if (hasDevModeResponse()) {
-                  subBuilder.mergeFrom(getDevModeResponse());
+              case 34: {
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.newBuilder();
+                if (hasDevModeRequest()) {
+                  subBuilder.mergeFrom(getDevModeRequest());
                 }
                 input.readMessage(subBuilder, extensionRegistry);
-                setDevModeResponse(subBuilder.buildPartial());
+                setDevModeRequest(subBuilder.buildPartial());
                 break;
               }
             }
           }
         }
-
-        public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-          if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response) {
-            return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response) other);
-          } else {
-            super.mergeFrom(other);
-            return this;
-          }
+        
+        
+        // required .com.google.gwt.dev.shell.remoteui.Message.Request.ServiceType serviceType = 1;
+        public boolean hasServiceType() {
+          return result.hasServiceType();
         }
-
-        public Builder mergeFrom(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response other) {
-          if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance())
-            return this;
-          if (other.hasRequestId()) {
-            setRequestId(other.getRequestId());
-          }
-          if (other.hasViewerResponse()) {
-            mergeViewerResponse(other.getViewerResponse());
-          }
-          if (other.hasDevModeResponse()) {
-            mergeDevModeResponse(other.getDevModeResponse());
-          }
-          this.mergeUnknownFields(other.getUnknownFields());
-          return this;
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType getServiceType() {
+          return result.getServiceType();
         }
-
-        public Builder mergeViewerResponse(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse value) {
-          if (result.hasViewerResponse()
-              && result.viewerResponse_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance()) {
-            result.viewerResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.newBuilder(
-                result.viewerResponse_).mergeFrom(value).buildPartial();
-          } else {
-            result.viewerResponse_ = value;
-          }
-          result.hasViewerResponse = true;
-          return this;
-        }
-
-        public Builder setDevModeResponse(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse value) {
+        public Builder setServiceType(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType value) {
           if (value == null) {
             throw new NullPointerException();
           }
-          result.hasDevModeResponse = true;
-          result.devModeResponse_ = value;
+          result.hasServiceType = true;
+          result.serviceType_ = value;
           return this;
         }
-
-        public Builder setDevModeResponse(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.Builder builderForValue) {
-          result.hasDevModeResponse = true;
-          result.devModeResponse_ = builderForValue.build();
+        public Builder clearServiceType() {
+          result.hasServiceType = false;
+          result.serviceType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ServiceType.VIEWER;
           return this;
         }
-
+        
+        // optional uint32 requestId = 2;
+        public boolean hasRequestId() {
+          return result.hasRequestId();
+        }
+        public int getRequestId() {
+          return result.getRequestId();
+        }
         public Builder setRequestId(int value) {
           result.hasRequestId = true;
           result.requestId_ = value;
           return this;
         }
-
-        public Builder setViewerResponse(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse value) {
+        public Builder clearRequestId() {
+          result.hasRequestId = false;
+          result.requestId_ = 0;
+          return this;
+        }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest viewerRequest = 3;
+        public boolean hasViewerRequest() {
+          return result.hasViewerRequest();
+        }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest getViewerRequest() {
+          return result.getViewerRequest();
+        }
+        public Builder setViewerRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest value) {
           if (value == null) {
             throw new NullPointerException();
           }
-          result.hasViewerResponse = true;
-          result.viewerResponse_ = value;
+          result.hasViewerRequest = true;
+          result.viewerRequest_ = value;
           return this;
         }
-
-        public Builder setViewerResponse(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.Builder builderForValue) {
-          result.hasViewerResponse = true;
-          result.viewerResponse_ = builderForValue.build();
+        public Builder setViewerRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Builder builderForValue) {
+          result.hasViewerRequest = true;
+          result.viewerRequest_ = builderForValue.build();
           return this;
         }
-
-        protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response internalGetResult() {
-          return result;
-        }
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response buildParsed()
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          if (!isInitialized()) {
-            throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
+        public Builder mergeViewerRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest value) {
+          if (result.hasViewerRequest() &&
+              result.viewerRequest_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance()) {
+            result.viewerRequest_ =
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.newBuilder(result.viewerRequest_).mergeFrom(value).buildPartial();
+          } else {
+            result.viewerRequest_ = value;
           }
-          return buildPartial();
+          result.hasViewerRequest = true;
+          return this;
+        }
+        public Builder clearViewerRequest() {
+          result.hasViewerRequest = false;
+          result.viewerRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.getDefaultInstance();
+          return this;
+        }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest devModeRequest = 4;
+        public boolean hasDevModeRequest() {
+          return result.hasDevModeRequest();
+        }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest getDevModeRequest() {
+          return result.getDevModeRequest();
+        }
+        public Builder setDevModeRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest value) {
+          if (value == null) {
+            throw new NullPointerException();
+          }
+          result.hasDevModeRequest = true;
+          result.devModeRequest_ = value;
+          return this;
+        }
+        public Builder setDevModeRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.Builder builderForValue) {
+          result.hasDevModeRequest = true;
+          result.devModeRequest_ = builderForValue.build();
+          return this;
+        }
+        public Builder mergeDevModeRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest value) {
+          if (result.hasDevModeRequest() &&
+              result.devModeRequest_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance()) {
+            result.devModeRequest_ =
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.newBuilder(result.devModeRequest_).mergeFrom(value).buildPartial();
+          } else {
+            result.devModeRequest_ = value;
+          }
+          result.hasDevModeRequest = true;
+          return this;
+        }
+        public Builder clearDevModeRequest() {
+          result.hasDevModeRequest = false;
+          result.devModeRequest_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.getDefaultInstance();
+          return this;
         }
       }
-
-      public static final class DevModeResponse extends
+      
+      static {
+        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+      }
+      
+      static {
+        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+      }
+    }
+    
+    public static final class Response extends
+        com.google.gwt.dev.protobuf.GeneratedMessage {
+      // Use Response.newBuilder() to construct.
+      private Response() {}
+      
+      private static final Response defaultInstance = new Response();
+      public static Response getDefaultInstance() {
+        return defaultInstance;
+      }
+      
+      public Response getDefaultInstanceForType() {
+        return defaultInstance;
+      }
+      
+      public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+          getDescriptor() {
+        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor;
+      }
+      
+      protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+          internalGetFieldAccessorTable() {
+        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_fieldAccessorTable;
+      }
+      
+      public static final class ViewerResponse extends
           com.google.gwt.dev.protobuf.GeneratedMessage {
-        public static final class Builder extends
-            com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-          private static Builder create() {
-            Builder builder = new Builder();
-            builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse();
-            return builder;
-          }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse result;
-
-          // Construct using
-          // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.newBuilder()
-          private Builder() {
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse build() {
-            if (result != null && !isInitialized()) {
-              throw newUninitializedMessageException(result);
-            }
-            return buildPartial();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse buildPartial() {
-            if (result == null) {
-              throw new IllegalStateException(
-                  "build() has already been called on this Builder.");
-            }
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse returnMe = result;
-            result = null;
-            return returnMe;
-          }
-
-          public Builder clear() {
-            if (result == null) {
-              throw new IllegalStateException(
-                  "Cannot call clear() after build().");
-            }
-            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse();
-            return this;
-          }
-
-          public Builder clearCapabilityExchange() {
-            result.hasCapabilityExchange = false;
-            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearResponseType() {
-            result.hasResponseType = false;
-            result.responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType.CAPABILITY_EXCHANGE;
-            return this;
-          }
-
-          public Builder clearRestartWebServer() {
-            result.hasRestartWebServer = false;
-            result.restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clone() {
-            return create().mergeFrom(result);
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange getCapabilityExchange() {
-            return result.getCapabilityExchange();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse getDefaultInstanceForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance();
-          }
-
-          public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDescriptor();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType getResponseType() {
-            return result.getResponseType();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer getRestartWebServer() {
-            return result.getRestartWebServer();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange
-          // capabilityExchange = 2;
-          public boolean hasCapabilityExchange() {
-            return result.hasCapabilityExchange();
-          }
-
-          // required
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.ResponseType
-          // responseType = 1;
-          public boolean hasResponseType() {
-            return result.hasResponseType();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.RestartWebServer
-          // restartWebServer = 3;
-          public boolean hasRestartWebServer() {
-            return result.hasRestartWebServer();
-          }
-
-          public boolean isInitialized() {
-            return result.isInitialized();
-          }
-
-          public Builder mergeCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange value) {
-            if (result.hasCapabilityExchange()
-                && result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance()) {
-              result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.newBuilder(
-                  result.capabilityExchange_).mergeFrom(value).buildPartial();
-            } else {
-              result.capabilityExchange_ = value;
-            }
-            result.hasCapabilityExchange = true;
-            return this;
-          }
-
-          public Builder mergeFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-            while (true) {
-              int tag = input.readTag();
-              switch (tag) {
-                case 0:
-                  this.setUnknownFields(unknownFields.build());
-                  return this;
-                default: {
-                  if (!parseUnknownField(input, unknownFields,
-                      extensionRegistry, tag)) {
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  }
-                  break;
-                }
-                case 8: {
-                  int rawValue = input.readEnum();
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType.valueOf(rawValue);
-                  if (value == null) {
-                    unknownFields.mergeVarintField(1, rawValue);
-                  } else {
-                    setResponseType(value);
-                  }
-                  break;
-                }
-                case 18: {
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.newBuilder();
-                  if (hasCapabilityExchange()) {
-                    subBuilder.mergeFrom(getCapabilityExchange());
-                  }
-                  input.readMessage(subBuilder, extensionRegistry);
-                  setCapabilityExchange(subBuilder.buildPartial());
-                  break;
-                }
-                case 26: {
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.newBuilder();
-                  if (hasRestartWebServer()) {
-                    subBuilder.mergeFrom(getRestartWebServer());
-                  }
-                  input.readMessage(subBuilder, extensionRegistry);
-                  setRestartWebServer(subBuilder.buildPartial());
-                  break;
-                }
-              }
+        // Use ViewerResponse.newBuilder() to construct.
+        private ViewerResponse() {}
+        
+        private static final ViewerResponse defaultInstance = new ViewerResponse();
+        public static ViewerResponse getDefaultInstance() {
+          return defaultInstance;
+        }
+        
+        public ViewerResponse getDefaultInstanceForType() {
+          return defaultInstance;
+        }
+        
+        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+            getDescriptor() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor;
+        }
+        
+        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+            internalGetFieldAccessorTable() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_fieldAccessorTable;
+        }
+        
+        public enum ResponseType
+            implements com.google.gwt.dev.protobuf.ProtocolMessageEnum {
+          CAPABILITY_EXCHANGE(0, 0),
+          ADD_LOG(1, 1),
+          ADD_LOG_BRANCH(2, 2),
+          ;
+          
+          
+          public final int getNumber() { return value; }
+          
+          public static ResponseType valueOf(int value) {
+            switch (value) {
+              case 0: return CAPABILITY_EXCHANGE;
+              case 1: return ADD_LOG;
+              case 2: return ADD_LOG_BRANCH;
+              default: return null;
             }
           }
-
-          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse) {
-              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse) other);
-            } else {
-              super.mergeFrom(other);
-              return this;
-            }
+          
+          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>
+              internalGetValueMap() {
+            return internalValueMap;
           }
-
-          public Builder mergeFrom(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse other) {
-            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance())
-              return this;
-            if (other.hasResponseType()) {
-              setResponseType(other.getResponseType());
-            }
-            if (other.hasCapabilityExchange()) {
-              mergeCapabilityExchange(other.getCapabilityExchange());
-            }
-            if (other.hasRestartWebServer()) {
-              mergeRestartWebServer(other.getRestartWebServer());
-            }
-            this.mergeUnknownFields(other.getUnknownFields());
-            return this;
+          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>
+              internalValueMap =
+                new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>() {
+                  public ResponseType findValueByNumber(int number) {
+                    return ResponseType.valueOf(number)
+          ;        }
+                };
+          
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor
+              getValueDescriptor() {
+            return getDescriptor().getValues().get(index);
           }
-
-          public Builder mergeRestartWebServer(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer value) {
-            if (result.hasRestartWebServer()
-                && result.restartWebServer_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance()) {
-              result.restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.newBuilder(
-                  result.restartWebServer_).mergeFrom(value).buildPartial();
-            } else {
-              result.restartWebServer_ = value;
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptorForType() {
+            return getDescriptor();
+          }
+          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDescriptor().getEnumTypes().get(0);
+          }
+          
+          private static final ResponseType[] VALUES = {
+            CAPABILITY_EXCHANGE, ADD_LOG, ADD_LOG_BRANCH, 
+          };
+          public static ResponseType valueOf(
+              com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
+            if (desc.getType() != getDescriptor()) {
+              throw new java.lang.IllegalArgumentException(
+                "EnumValueDescriptor is not for this type.");
             }
-            result.hasRestartWebServer = true;
-            return this;
+            return VALUES[desc.getIndex()];
           }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = value;
-            return this;
+          private final int index;
+          private final int value;
+          private ResponseType(int index, int value) {
+            this.index = index;
+            this.value = value;
           }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Builder builderForValue) {
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setResponseType(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasResponseType = true;
-            result.responseType_ = value;
-            return this;
-          }
-
-          public Builder setRestartWebServer(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasRestartWebServer = true;
-            result.restartWebServer_ = value;
-            return this;
-          }
-
-          public Builder setRestartWebServer(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.Builder builderForValue) {
-            result.hasRestartWebServer = true;
-            result.restartWebServer_ = builderForValue.build();
-            return this;
-          }
-
-          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse internalGetResult() {
-            return result;
-          }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse buildParsed()
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            if (!isInitialized()) {
-              throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-            }
-            return buildPartial();
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
         }
-
+        
         public static final class CapabilityExchange extends
             com.google.gwt.dev.protobuf.GeneratedMessage {
-          public static final class Builder extends
-              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-            private static Builder create() {
-              Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange();
-              return builder;
+          // Use CapabilityExchange.newBuilder() to construct.
+          private CapabilityExchange() {}
+          
+          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
+          public static CapabilityExchange getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public CapabilityExchange getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_fieldAccessorTable;
+          }
+          
+          public static final class Capability extends
+              com.google.gwt.dev.protobuf.GeneratedMessage {
+            // Use Capability.newBuilder() to construct.
+            private Capability() {}
+            
+            private static final Capability defaultInstance = new Capability();
+            public static Capability getDefaultInstance() {
+              return defaultInstance;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.newBuilder()
-            private Builder() {
+            
+            public Capability getDefaultInstanceForType() {
+              return defaultInstance;
             }
-
-            public Builder addAllCapabilities(
-                java.lang.Iterable<? extends com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> values) {
-              if (result.capabilities_.isEmpty()) {
-                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
+            
+            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptor() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor;
+            }
+            
+            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+                internalGetFieldAccessorTable() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_fieldAccessorTable;
+            }
+            
+            // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType capability = 1;
+            public static final int CAPABILITY_FIELD_NUMBER = 1;
+            private boolean hasCapability;
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
+            public boolean hasCapability() { return hasCapability; }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getCapability() { return capability_; }
+            
+            public final boolean isInitialized() {
+              if (!hasCapability) return false;
+              return true;
+            }
+            
+            public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                                throws java.io.IOException {
+              if (hasCapability()) {
+                output.writeEnum(1, getCapability().getNumber());
               }
-              super.addAll(values, result.capabilities_);
-              return this;
+              getUnknownFields().writeTo(output);
             }
-
-            public Builder addCapabilities(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability value) {
-              if (value == null) {
-                throw new NullPointerException();
+            
+            private int memoizedSerializedSize = -1;
+            public int getSerializedSize() {
+              int size = memoizedSerializedSize;
+              if (size != -1) return size;
+            
+              size = 0;
+              if (hasCapability()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeEnumSize(1, getCapability().getNumber());
               }
-              if (result.capabilities_.isEmpty()) {
-                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
-              }
-              result.capabilities_.add(value);
-              return this;
+              size += getUnknownFields().getSerializedSize();
+              memoizedSerializedSize = size;
+              return size;
             }
-
-            public Builder addCapabilities(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder builderForValue) {
-              if (result.capabilities_.isEmpty()) {
-                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
-              }
-              result.capabilities_.add(builderForValue.build());
-              return this;
+            
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange build() {
-              if (result != null && !isInitialized()) {
-                throw newUninitializedMessageException(result);
-              }
-              return buildPartial();
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange buildPartial() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
-              }
-              if (result.capabilities_ != java.util.Collections.EMPTY_LIST) {
-                result.capabilities_ = java.util.Collections.unmodifiableList(result.capabilities_);
-              }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange returnMe = result;
-              result = null;
-              return returnMe;
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(byte[] data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
-              }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange();
-              return this;
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
+                byte[] data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
             }
-
-            public Builder clearCapabilities() {
-              result.capabilities_ = java.util.Collections.emptyList();
-              return this;
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
             }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability getCapabilities(
-                int index) {
-              return result.getCapabilities(index);
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseDelimitedFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input).buildParsed();
             }
-
-            public int getCapabilitiesCount() {
-              return result.getCapabilitiesCount();
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseDelimitedFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                       .buildParsed();
             }
-
-            // repeated
-            // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange.Capability
-            // capabilities = 2;
-            public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> getCapabilitiesList() {
-              return java.util.Collections.unmodifiableList(result.capabilities_);
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDescriptor();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
-            public Builder mergeFrom(
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-              while (true) {
-                int tag = input.readTag();
-                switch (tag) {
-                  case 0:
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  default: {
-                    if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    }
-                    break;
-                  }
-                  case 18: {
-                    com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.newBuilder();
-                    input.readMessage(subBuilder, extensionRegistry);
-                    addCapabilities(subBuilder.buildPartial());
-                    break;
-                  }
-                }
-              }
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            public static Builder newBuilder() { return Builder.create(); }
+            public Builder newBuilderForType() { return newBuilder(); }
+            public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability prototype) {
+              return newBuilder().mergeFrom(prototype);
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance())
-                return this;
-              if (!other.capabilities_.isEmpty()) {
-                if (result.capabilities_.isEmpty()) {
-                  result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
-                }
-                result.capabilities_.addAll(other.capabilities_);
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
-            }
-
-            public Builder setCapabilities(
-                int index,
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.capabilities_.set(index, value);
-              return this;
-            }
-
-            public Builder setCapabilities(
-                int index,
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder builderForValue) {
-              result.capabilities_.set(index, builderForValue.build());
-              return this;
-            }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
-            }
-          }
-
-          public static final class Capability extends
-              com.google.gwt.dev.protobuf.GeneratedMessage {
+            public Builder toBuilder() { return newBuilder(this); }
+            
             public static final class Builder extends
                 com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability result;
+              
+              // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.newBuilder()
+              private Builder() {}
+              
               private static Builder create() {
                 Builder builder = new Builder();
-                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability();
+                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability();
                 return builder;
               }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability result;
-
-              // Construct using
-              // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.newBuilder()
-              private Builder() {
+              
+              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability internalGetResult() {
+                return result;
               }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability build() {
+              
+              public Builder clear() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "Cannot call clear() after build().");
+                }
+                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability();
+                return this;
+              }
+              
+              public Builder clone() {
+                return create().mergeFrom(result);
+              }
+              
+              public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                  getDescriptorForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.getDescriptor();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability getDefaultInstanceForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.getDefaultInstance();
+              }
+              
+              public boolean isInitialized() {
+                return result.isInitialized();
+              }
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability build() {
                 if (result != null && !isInitialized()) {
                   throw newUninitializedMessageException(result);
                 }
                 return buildPartial();
               }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability buildPartial() {
+              
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability buildParsed()
+                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+                if (!isInitialized()) {
+                  throw newUninitializedMessageException(
+                    result).asInvalidProtocolBufferException();
+                }
+                return buildPartial();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability buildPartial() {
                 if (result == null) {
                   throw new IllegalStateException(
-                      "build() has already been called on this Builder.");
+                    "build() has already been called on this Builder.");
                 }
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability returnMe = result;
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability returnMe = result;
                 result = null;
                 return returnMe;
               }
-
-              public Builder clear() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "Cannot call clear() after build().");
+              
+              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability) {
+                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability)other);
+                } else {
+                  super.mergeFrom(other);
+                  return this;
                 }
-                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability();
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability other) {
+                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.getDefaultInstance()) return this;
+                if (other.hasCapability()) {
+                  setCapability(other.getCapability());
+                }
+                this.mergeUnknownFields(other.getUnknownFields());
                 return this;
               }
-
-              public Builder clearCapability() {
-                result.hasCapability = false;
-                result.capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
-                return this;
-              }
-
-              public Builder clone() {
-                return create().mergeFrom(result);
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getCapability() {
-                return result.getCapability();
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability getDefaultInstanceForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.getDefaultInstance();
-              }
-
-              public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.getDescriptor();
-              }
-
-              // required
-              // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType
-              // capability = 1;
-              public boolean hasCapability() {
-                return result.hasCapability();
-              }
-
-              public boolean isInitialized() {
-                return result.isInitialized();
-              }
-
+              
               public Builder mergeFrom(
                   com.google.gwt.dev.protobuf.CodedInputStream input,
                   com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                   throws java.io.IOException {
-                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                  com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                    this.getUnknownFields());
                 while (true) {
                   int tag = input.readTag();
                   switch (tag) {
@@ -7648,7 +6563,7 @@
                       return this;
                     default: {
                       if (!parseUnknownField(input, unknownFields,
-                          extensionRegistry, tag)) {
+                                             extensionRegistry, tag)) {
                         this.setUnknownFields(unknownFields.build());
                         return this;
                       }
@@ -7656,7 +6571,7 @@
                     }
                     case 8: {
                       int rawValue = input.readEnum();
-                      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.valueOf(rawValue);
+                      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.valueOf(rawValue);
                       if (value == null) {
                         unknownFields.mergeVarintField(1, rawValue);
                       } else {
@@ -7667,29 +6582,16 @@
                   }
                 }
               }
-
-              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability) {
-                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability) other);
-                } else {
-                  super.mergeFrom(other);
-                  return this;
-                }
+              
+              
+              // required .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType capability = 1;
+              public boolean hasCapability() {
+                return result.hasCapability();
               }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability other) {
-                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.getDefaultInstance())
-                  return this;
-                if (other.hasCapability()) {
-                  setCapability(other.getCapability());
-                }
-                this.mergeUnknownFields(other.getUnknownFields());
-                return this;
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getCapability() {
+                return result.getCapability();
               }
-
-              public Builder setCapability(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value) {
+              public Builder setCapability(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType value) {
                 if (value == null) {
                   throw new NullPointerException();
                 }
@@ -7697,471 +6599,229 @@
                 result.capability_ = value;
                 return this;
               }
-
-              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability internalGetResult() {
-                return result;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability buildParsed()
-                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-                if (!isInitialized()) {
-                  throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-                }
-                return buildPartial();
+              public Builder clearCapability() {
+                result.hasCapability = false;
+                result.capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
+                return this;
               }
             }
-
-            private static final Capability defaultInstance = new Capability();
-            // required
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType
-            // capability = 1;
-            public static final int CAPABILITY_FIELD_NUMBER = 1;
-
+            
             static {
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
             }
-
+            
             static {
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
             }
-
-            public static Capability getDefaultInstance() {
-              return defaultInstance;
-            }
-
-            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor;
-            }
-
-            public static Builder newBuilder() {
-              return Builder.create();
-            }
-
-            public static Builder newBuilder(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability prototype) {
-              return newBuilder().mergeFrom(prototype);
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseDelimitedFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseDelimitedFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                byte[] data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                byte[] data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            private boolean hasCapability;
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
-            private int memoizedSerializedSize = -1;
-
-            // Use Capability.newBuilder() to construct.
-            private Capability() {
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getCapability() {
-              return capability_;
-            }
-
-            public Capability getDefaultInstanceForType() {
-              return defaultInstance;
-            }
-
-            public int getSerializedSize() {
-              int size = memoizedSerializedSize;
-              if (size != -1)
-                return size;
-
-              size = 0;
-              if (hasCapability()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-                    1, getCapability().getNumber());
-              }
-              size += getUnknownFields().getSerializedSize();
-              memoizedSerializedSize = size;
-              return size;
-            }
-
-            public boolean hasCapability() {
-              return hasCapability;
-            }
-
-            public final boolean isInitialized() {
-              if (!hasCapability)
-                return false;
-              return true;
-            }
-
-            public Builder newBuilderForType() {
-              return newBuilder();
-            }
-
-            public Builder toBuilder() {
-              return newBuilder(this);
-            }
-
-            public void writeTo(
-                com.google.gwt.dev.protobuf.CodedOutputStream output)
-                throws java.io.IOException {
-              if (hasCapability()) {
-                output.writeEnum(1, getCapability().getNumber());
-              }
-              getUnknownFields().writeTo(output);
-            }
-
-            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_fieldAccessorTable;
-            }
           }
-
-          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
-
-          // repeated
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange.Capability
-          // capabilities = 2;
+          
+          // repeated .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange.Capability capabilities = 2;
           public static final int CAPABILITIES_FIELD_NUMBER = 2;
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static CapabilityExchange getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> capabilities_ = java.util.Collections.emptyList();
-          private int memoizedSerializedSize = -1;
-
-          // Use CapabilityExchange.newBuilder() to construct.
-          private CapabilityExchange() {
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability getCapabilities(
-              int index) {
-            return capabilities_.get(index);
-          }
-
-          public int getCapabilitiesCount() {
-            return capabilities_.size();
-          }
-
-          public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> getCapabilitiesList() {
+          private java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> capabilities_ =
+            java.util.Collections.emptyList();
+          public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> getCapabilitiesList() {
             return capabilities_;
           }
-
-          public CapabilityExchange getDefaultInstanceForType() {
-            return defaultInstance;
+          public int getCapabilitiesCount() { return capabilities_.size(); }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability getCapabilities(int index) {
+            return capabilities_.get(index);
           }
-
+          
+          public final boolean isInitialized() {
+            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
+              if (!element.isInitialized()) return false;
+            }
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
+              output.writeMessage(2, element);
+            }
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
           public int getSerializedSize() {
             int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
+            if (size != -1) return size;
+          
             size = 0;
-            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  2, element);
+            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(2, element);
             }
             size += getUnknownFields().getSerializedSize();
             memoizedSerializedSize = size;
             return size;
           }
-
-          public final boolean isInitialized() {
-            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
-              if (!element.isInitialized())
-                return false;
-            }
-            return true;
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(java.io.InputStream input)
               throws java.io.IOException {
-            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
-              output.writeMessage(2, element);
-            }
-            getUnknownFields().writeTo(output);
+            return newBuilder().mergeFrom(input).buildParsed();
           }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_fieldAccessorTable;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
           }
-        }
-        public enum ResponseType implements
-            com.google.gwt.dev.protobuf.ProtocolMessageEnum {
-          CAPABILITY_EXCHANGE(0, 0), RESTART_WEB_SERVER(1, 1), ;
-
-          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType> internalValueMap = new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>() {
-            public ResponseType findValueByNumber(int number) {
-              return ResponseType.valueOf(number);
-            }
-          };
-
-          private static final ResponseType[] VALUES = {
-              CAPABILITY_EXCHANGE, RESTART_WEB_SERVER,};
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDescriptor().getEnumTypes().get(
-                0);
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
           }
-
-          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType> internalGetValueMap() {
-            return internalValueMap;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
           }
-
-          public static ResponseType valueOf(
-              com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
-            if (desc.getType() != getDescriptor()) {
-              throw new java.lang.IllegalArgumentException(
-                  "EnumValueDescriptor is not for this type.");
-            }
-            return VALUES[desc.getIndex()];
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
           }
-
-          public static ResponseType valueOf(int value) {
-            switch (value) {
-              case 0:
-                return CAPABILITY_EXCHANGE;
-              case 1:
-                return RESTART_WEB_SERVER;
-              default:
-                return null;
-            }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
           }
-
-          private final int index;
-
-          private final int value;
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange prototype) {
+            return newBuilder().mergeFrom(prototype);
           }
-
-          private ResponseType(int index, int value) {
-            this.index = index;
-            this.value = value;
-          }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptorForType() {
-            return getDescriptor();
-          }
-
-          public final int getNumber() {
-            return value;
-          }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() {
-            return getDescriptor().getValues().get(index);
-          }
-        }
-
-        public static final class RestartWebServer extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
+          public Builder toBuilder() { return newBuilder(this); }
+          
           public static final class Builder extends
               com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.newBuilder()
+            private Builder() {}
+            
             private static Builder create() {
               Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange();
               return builder;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.newBuilder()
-            private Builder() {
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange internalGetResult() {
+              return result;
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer build() {
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange build() {
               if (result != null && !isInitialized()) {
                 throw newUninitializedMessageException(result);
               }
               return buildPartial();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer buildPartial() {
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange buildPartial() {
               if (result == null) {
                 throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
+                  "build() has already been called on this Builder.");
               }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer returnMe = result;
+              if (result.capabilities_ != java.util.Collections.EMPTY_LIST) {
+                result.capabilities_ =
+                  java.util.Collections.unmodifiableList(result.capabilities_);
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange returnMe = result;
               result = null;
               return returnMe;
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
               }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer();
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance()) return this;
+              if (!other.capabilities_.isEmpty()) {
+                if (result.capabilities_.isEmpty()) {
+                  result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
+                }
+                result.capabilities_.addAll(other.capabilities_);
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
               return this;
             }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDescriptor();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
+            
             public Builder mergeFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
               while (true) {
                 int tag = input.readTag();
                 switch (tag) {
@@ -8170,467 +6830,301 @@
                     return this;
                   default: {
                     if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
+                                           extensionRegistry, tag)) {
                       this.setUnknownFields(unknownFields.build());
                       return this;
                     }
                     break;
                   }
+                  case 18: {
+                    com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.newBuilder();
+                    input.readMessage(subBuilder, extensionRegistry);
+                    addCapabilities(subBuilder.buildPartial());
+                    break;
+                  }
                 }
               }
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            
+            // repeated .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange.Capability capabilities = 2;
+            public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> getCapabilitiesList() {
+              return java.util.Collections.unmodifiableList(result.capabilities_);
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance())
-                return this;
-              this.mergeUnknownFields(other.getUnknownFields());
+            public int getCapabilitiesCount() {
+              return result.getCapabilitiesCount();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability getCapabilities(int index) {
+              return result.getCapabilities(index);
+            }
+            public Builder setCapabilities(int index, com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability value) {
+              if (value == null) {
+                throw new NullPointerException();
+              }
+              result.capabilities_.set(index, value);
               return this;
             }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer internalGetResult() {
-              return result;
+            public Builder setCapabilities(int index, com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder builderForValue) {
+              result.capabilities_.set(index, builderForValue.build());
+              return this;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
+            public Builder addCapabilities(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability value) {
+              if (value == null) {
+                throw new NullPointerException();
               }
-              return buildPartial();
+              if (result.capabilities_.isEmpty()) {
+                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
+              }
+              result.capabilities_.add(value);
+              return this;
             }
-
+            public Builder addCapabilities(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder builderForValue) {
+              if (result.capabilities_.isEmpty()) {
+                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
+              }
+              result.capabilities_.add(builderForValue.build());
+              return this;
+            }
+            public Builder addAllCapabilities(
+                java.lang.Iterable<? extends com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> values) {
+              if (result.capabilities_.isEmpty()) {
+                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
+              }
+              super.addAll(values, result.capabilities_);
+              return this;
+            }
+            public Builder clearCapabilities() {
+              result.capabilities_ = java.util.Collections.emptyList();
+              return this;
+            }
           }
-
-          private static final RestartWebServer defaultInstance = new RestartWebServer();
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
           }
-
-          public static RestartWebServer getDefaultInstance() {
+        }
+        
+        public static final class AddLog extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use AddLog.newBuilder() to construct.
+          private AddLog() {}
+          
+          private static final AddLog defaultInstance = new AddLog();
+          public static AddLog getDefaultInstance() {
             return defaultInstance;
           }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor;
+          
+          public AddLog getDefaultInstanceForType() {
+            return defaultInstance;
           }
-
-          public static Builder newBuilder() {
-            return Builder.create();
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor;
           }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer prototype) {
-            return newBuilder().mergeFrom(prototype);
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_fieldAccessorTable;
           }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          
+          // required uint32 logHandle = 1;
+          public static final int LOGHANDLE_FIELD_NUMBER = 1;
+          private boolean hasLogHandle;
+          private int logHandle_ = 0;
+          public boolean hasLogHandle() { return hasLogHandle; }
+          public int getLogHandle() { return logHandle_; }
+          
+          public final boolean isInitialized() {
+            if (!hasLogHandle) return false;
+            return true;
           }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            if (hasLogHandle()) {
+              output.writeUInt32(1, getLogHandle());
+            }
+            getUnknownFields().writeTo(output);
           }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
+          
           private int memoizedSerializedSize = -1;
-
-          // Use RestartWebServer.newBuilder() to construct.
-          private RestartWebServer() {
-          }
-
-          public RestartWebServer getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
           public int getSerializedSize() {
             int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
+            if (size != -1) return size;
+          
             size = 0;
+            if (hasLogHandle()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeUInt32Size(1, getLogHandle());
+            }
             size += getUnknownFields().getSerializedSize();
             memoizedSerializedSize = size;
             return size;
           }
-
-          public final boolean isInitialized() {
-            return true;
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(java.io.InputStream input)
               throws java.io.IOException {
-            getUnknownFields().writeTo(output);
+            return newBuilder().mergeFrom(input).buildParsed();
           }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_fieldAccessorTable;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
           }
-        }
-
-        private static final DevModeResponse defaultInstance = new DevModeResponse();
-
-        // required
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.ResponseType
-        // responseType = 1;
-        public static final int RESPONSETYPE_FIELD_NUMBER = 1;
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-        }
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-        }
-
-        public static DevModeResponse getDefaultInstance() {
-          return defaultInstance;
-        }
-
-        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor;
-        }
-
-        public static Builder newBuilder() {
-          return Builder.create();
-        }
-
-        public static Builder newBuilder(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse prototype) {
-          return newBuilder().mergeFrom(prototype);
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseDelimitedFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseDelimitedFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            byte[] data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            byte[] data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
-        private boolean hasResponseType;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType.CAPABILITY_EXCHANGE;
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange
-        // capabilityExchange = 2;
-        public static final int CAPABILITYEXCHANGE_FIELD_NUMBER = 2;
-
-        private boolean hasCapabilityExchange;
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance();
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.RestartWebServer
-        // restartWebServer = 3;
-        public static final int RESTARTWEBSERVER_FIELD_NUMBER = 3;
-
-        private boolean hasRestartWebServer;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance();
-        private int memoizedSerializedSize = -1;
-
-        // Use DevModeResponse.newBuilder() to construct.
-        private DevModeResponse() {
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange getCapabilityExchange() {
-          return capabilityExchange_;
-        }
-
-        public DevModeResponse getDefaultInstanceForType() {
-          return defaultInstance;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType getResponseType() {
-          return responseType_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer getRestartWebServer() {
-          return restartWebServer_;
-        }
-
-        public int getSerializedSize() {
-          int size = memoizedSerializedSize;
-          if (size != -1)
-            return size;
-
-          size = 0;
-          if (hasResponseType()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-                1, getResponseType().getNumber());
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
           }
-          if (hasCapabilityExchange()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                2, getCapabilityExchange());
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
           }
-          if (hasRestartWebServer()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                3, getRestartWebServer());
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
           }
-          size += getUnknownFields().getSerializedSize();
-          memoizedSerializedSize = size;
-          return size;
-        }
-
-        public boolean hasCapabilityExchange() {
-          return hasCapabilityExchange;
-        }
-
-        public boolean hasResponseType() {
-          return hasResponseType;
-        }
-
-        public boolean hasRestartWebServer() {
-          return hasRestartWebServer;
-        }
-
-        public final boolean isInitialized() {
-          if (!hasResponseType)
-            return false;
-          if (hasCapabilityExchange()) {
-            if (!getCapabilityExchange().isInitialized())
-              return false;
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
           }
-          return true;
-        }
-
-        public Builder newBuilderForType() {
-          return newBuilder();
-        }
-
-        public Builder toBuilder() {
-          return newBuilder(this);
-        }
-
-        public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
-            throws java.io.IOException {
-          if (hasResponseType()) {
-            output.writeEnum(1, getResponseType().getNumber());
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog prototype) {
+            return newBuilder().mergeFrom(prototype);
           }
-          if (hasCapabilityExchange()) {
-            output.writeMessage(2, getCapabilityExchange());
-          }
-          if (hasRestartWebServer()) {
-            output.writeMessage(3, getRestartWebServer());
-          }
-          getUnknownFields().writeTo(output);
-        }
-
-        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_fieldAccessorTable;
-        }
-      }
-      public static final class ViewerResponse extends
-          com.google.gwt.dev.protobuf.GeneratedMessage {
-        public static final class AddLog extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
+          public Builder toBuilder() { return newBuilder(this); }
+          
           public static final class Builder extends
               com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.newBuilder()
+            private Builder() {}
+            
             private static Builder create() {
               Builder builder = new Builder();
               builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog();
               return builder;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.newBuilder()
-            private Builder() {
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog internalGetResult() {
+              return result;
             }
-
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog build() {
               if (result != null && !isInitialized()) {
                 throw newUninitializedMessageException(result);
               }
               return buildPartial();
             }
-
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog buildPartial() {
               if (result == null) {
                 throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
+                  "build() has already been called on this Builder.");
               }
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog returnMe = result;
               result = null;
               return returnMe;
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
               }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog();
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance()) return this;
+              if (other.hasLogHandle()) {
+                setLogHandle(other.getLogHandle());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
               return this;
             }
-
-            public Builder clearLogHandle() {
-              result.hasLogHandle = false;
-              result.logHandle_ = 0;
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDescriptor();
-            }
-
-            public int getLogHandle() {
-              return result.getLogHandle();
-            }
-
-            // required uint32 logHandle = 1;
-            public boolean hasLogHandle() {
-              return result.hasLogHandle();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
+            
             public Builder mergeFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
               while (true) {
                 int tag = input.readTag();
                 switch (tag) {
@@ -8639,7 +7133,7 @@
                     return this;
                   default: {
                     if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
+                                           extensionRegistry, tag)) {
                       this.setUnknownFields(unknownFields.build());
                       return this;
                     }
@@ -8652,280 +7146,253 @@
                 }
               }
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            
+            // required uint32 logHandle = 1;
+            public boolean hasLogHandle() {
+              return result.hasLogHandle();
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance())
-                return this;
-              if (other.hasLogHandle()) {
-                setLogHandle(other.getLogHandle());
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
+            public int getLogHandle() {
+              return result.getLogHandle();
             }
-
             public Builder setLogHandle(int value) {
               result.hasLogHandle = true;
               result.logHandle_ = value;
               return this;
             }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
+            public Builder clearLogHandle() {
+              result.hasLogHandle = false;
+              result.logHandle_ = 0;
+              return this;
             }
           }
-
-          private static final AddLog defaultInstance = new AddLog();
-          // required uint32 logHandle = 1;
-          public static final int LOGHANDLE_FIELD_NUMBER = 1;
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
           }
-
-          public static AddLog getDefaultInstance() {
+        }
+        
+        public static final class AddLogBranch extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use AddLogBranch.newBuilder() to construct.
+          private AddLogBranch() {}
+          
+          private static final AddLogBranch defaultInstance = new AddLogBranch();
+          public static AddLogBranch getDefaultInstance() {
             return defaultInstance;
           }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor;
+          
+          public AddLogBranch getDefaultInstanceForType() {
+            return defaultInstance;
           }
-
-          public static Builder newBuilder() {
-            return Builder.create();
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor;
           }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog prototype) {
-            return newBuilder().mergeFrom(prototype);
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_fieldAccessorTable;
           }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
+          
+          // required uint32 logHandle = 1;
+          public static final int LOGHANDLE_FIELD_NUMBER = 1;
           private boolean hasLogHandle;
           private int logHandle_ = 0;
-          private int memoizedSerializedSize = -1;
-
-          // Use AddLog.newBuilder() to construct.
-          private AddLog() {
-          }
-
-          public AddLog getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getLogHandle() {
-            return logHandle_;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            if (hasLogHandle()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-                  1, getLogHandle());
-            }
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public boolean hasLogHandle() {
-            return hasLogHandle;
-          }
-
+          public boolean hasLogHandle() { return hasLogHandle; }
+          public int getLogHandle() { return logHandle_; }
+          
           public final boolean isInitialized() {
-            if (!hasLogHandle)
-              return false;
+            if (!hasLogHandle) return false;
             return true;
           }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
             if (hasLogHandle()) {
               output.writeUInt32(1, getLogHandle());
             }
             getUnknownFields().writeTo(output);
           }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_fieldAccessorTable;
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            if (hasLogHandle()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeUInt32Size(1, getLogHandle());
+            }
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
           }
-        }
-
-        public static final class AddLogBranch extends
-            com.google.gwt.dev.protobuf.GeneratedMessage {
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
           public static final class Builder extends
               com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.newBuilder()
+            private Builder() {}
+            
             private static Builder create() {
               Builder builder = new Builder();
               builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch();
               return builder;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.newBuilder()
-            private Builder() {
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch internalGetResult() {
+              return result;
             }
-
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch build() {
               if (result != null && !isInitialized()) {
                 throw newUninitializedMessageException(result);
               }
               return buildPartial();
             }
-
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
             public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch buildPartial() {
               if (result == null) {
                 throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
+                  "build() has already been called on this Builder.");
               }
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch returnMe = result;
               result = null;
               return returnMe;
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
               }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch();
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance()) return this;
+              if (other.hasLogHandle()) {
+                setLogHandle(other.getLogHandle());
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
               return this;
             }
-
-            public Builder clearLogHandle() {
-              result.hasLogHandle = false;
-              result.logHandle_ = 0;
-              return this;
-            }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDescriptor();
-            }
-
-            public int getLogHandle() {
-              return result.getLogHandle();
-            }
-
-            // required uint32 logHandle = 1;
-            public boolean hasLogHandle() {
-              return result.hasLogHandle();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
+            
             public Builder mergeFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
               while (true) {
                 int tag = input.readTag();
                 switch (tag) {
@@ -8934,7 +7401,7 @@
                     return this;
                   default: {
                     if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
+                                           extensionRegistry, tag)) {
                       this.setUnknownFields(unknownFields.build());
                       return this;
                     }
@@ -8947,369 +7414,289 @@
                 }
               }
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            
+            // required uint32 logHandle = 1;
+            public boolean hasLogHandle() {
+              return result.hasLogHandle();
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance())
-                return this;
-              if (other.hasLogHandle()) {
-                setLogHandle(other.getLogHandle());
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
+            public int getLogHandle() {
+              return result.getLogHandle();
             }
-
             public Builder setLogHandle(int value) {
               result.hasLogHandle = true;
               result.logHandle_ = value;
               return this;
             }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
+            public Builder clearLogHandle() {
+              result.hasLogHandle = false;
+              result.logHandle_ = 0;
+              return this;
             }
           }
-
-          private static final AddLogBranch defaultInstance = new AddLogBranch();
-          // required uint32 logHandle = 1;
-          public static final int LOGHANDLE_FIELD_NUMBER = 1;
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
-
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
           }
-
-          public static AddLogBranch getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private boolean hasLogHandle;
-          private int logHandle_ = 0;
-          private int memoizedSerializedSize = -1;
-
-          // Use AddLogBranch.newBuilder() to construct.
-          private AddLogBranch() {
-          }
-
-          public AddLogBranch getDefaultInstanceForType() {
-            return defaultInstance;
-          }
-
-          public int getLogHandle() {
-            return logHandle_;
-          }
-
-          public int getSerializedSize() {
-            int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
-            size = 0;
-            if (hasLogHandle()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-                  1, getLogHandle());
-            }
-            size += getUnknownFields().getSerializedSize();
-            memoizedSerializedSize = size;
-            return size;
-          }
-
-          public boolean hasLogHandle() {
-            return hasLogHandle;
-          }
-
-          public final boolean isInitialized() {
-            if (!hasLogHandle)
-              return false;
-            return true;
-          }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
-          }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
-          }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
-              throws java.io.IOException {
-            if (hasLogHandle()) {
-              output.writeUInt32(1, getLogHandle());
-            }
-            getUnknownFields().writeTo(output);
-          }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_fieldAccessorTable;
-          }
         }
+        
+        // required .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.ResponseType responseType = 1;
+        public static final int RESPONSETYPE_FIELD_NUMBER = 1;
+        private boolean hasResponseType;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType.CAPABILITY_EXCHANGE;
+        public boolean hasResponseType() { return hasResponseType; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType getResponseType() { return responseType_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange capabilityExchange = 2;
+        public static final int CAPABILITYEXCHANGE_FIELD_NUMBER = 2;
+        private boolean hasCapabilityExchange;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance();
+        public boolean hasCapabilityExchange() { return hasCapabilityExchange; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange getCapabilityExchange() { return capabilityExchange_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLog addLog = 3;
+        public static final int ADDLOG_FIELD_NUMBER = 3;
+        private boolean hasAddLog;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance();
+        public boolean hasAddLog() { return hasAddLog; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog getAddLog() { return addLog_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLogBranch addLogBranch = 4;
+        public static final int ADDLOGBRANCH_FIELD_NUMBER = 4;
+        private boolean hasAddLogBranch;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance();
+        public boolean hasAddLogBranch() { return hasAddLogBranch; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch getAddLogBranch() { return addLogBranch_; }
+        
+        public final boolean isInitialized() {
+          if (!hasResponseType) return false;
+          if (hasCapabilityExchange()) {
+            if (!getCapabilityExchange().isInitialized()) return false;
+          }
+          if (hasAddLog()) {
+            if (!getAddLog().isInitialized()) return false;
+          }
+          if (hasAddLogBranch()) {
+            if (!getAddLogBranch().isInitialized()) return false;
+          }
+          return true;
+        }
+        
+        public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                            throws java.io.IOException {
+          if (hasResponseType()) {
+            output.writeEnum(1, getResponseType().getNumber());
+          }
+          if (hasCapabilityExchange()) {
+            output.writeMessage(2, getCapabilityExchange());
+          }
+          if (hasAddLog()) {
+            output.writeMessage(3, getAddLog());
+          }
+          if (hasAddLogBranch()) {
+            output.writeMessage(4, getAddLogBranch());
+          }
+          getUnknownFields().writeTo(output);
+        }
+        
+        private int memoizedSerializedSize = -1;
+        public int getSerializedSize() {
+          int size = memoizedSerializedSize;
+          if (size != -1) return size;
+        
+          size = 0;
+          if (hasResponseType()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeEnumSize(1, getResponseType().getNumber());
+          }
+          if (hasCapabilityExchange()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(2, getCapabilityExchange());
+          }
+          if (hasAddLog()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(3, getAddLog());
+          }
+          if (hasAddLogBranch()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(4, getAddLogBranch());
+          }
+          size += getUnknownFields().getSerializedSize();
+          memoizedSerializedSize = size;
+          return size;
+        }
+        
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(byte[] data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
+            byte[] data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseDelimitedFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseDelimitedFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        
+        public static Builder newBuilder() { return Builder.create(); }
+        public Builder newBuilderForType() { return newBuilder(); }
+        public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse prototype) {
+          return newBuilder().mergeFrom(prototype);
+        }
+        public Builder toBuilder() { return newBuilder(this); }
+        
         public static final class Builder extends
             com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse result;
+          
+          // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.newBuilder()
+          private Builder() {}
+          
           private static Builder create() {
             Builder builder = new Builder();
             builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse();
             return builder;
           }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse result;
-
-          // Construct using
-          // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.newBuilder()
-          private Builder() {
+          
+          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse internalGetResult() {
+            return result;
           }
-
+          
+          public Builder clear() {
+            if (result == null) {
+              throw new IllegalStateException(
+                "Cannot call clear() after build().");
+            }
+            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse();
+            return this;
+          }
+          
+          public Builder clone() {
+            return create().mergeFrom(result);
+          }
+          
+          public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptorForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDescriptor();
+          }
+          
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse getDefaultInstanceForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance();
+          }
+          
+          public boolean isInitialized() {
+            return result.isInitialized();
+          }
           public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse build() {
             if (result != null && !isInitialized()) {
               throw newUninitializedMessageException(result);
             }
             return buildPartial();
           }
-
+          
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse buildParsed()
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            if (!isInitialized()) {
+              throw newUninitializedMessageException(
+                result).asInvalidProtocolBufferException();
+            }
+            return buildPartial();
+          }
+          
           public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse buildPartial() {
             if (result == null) {
               throw new IllegalStateException(
-                  "build() has already been called on this Builder.");
+                "build() has already been called on this Builder.");
             }
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse returnMe = result;
             result = null;
             return returnMe;
           }
-
-          public Builder clear() {
-            if (result == null) {
-              throw new IllegalStateException(
-                  "Cannot call clear() after build().");
-            }
-            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse();
-            return this;
-          }
-
-          public Builder clearAddLog() {
-            result.hasAddLog = false;
-            result.addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearAddLogBranch() {
-            result.hasAddLogBranch = false;
-            result.addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearCapabilityExchange() {
-            result.hasCapabilityExchange = false;
-            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance();
-            return this;
-          }
-
-          public Builder clearResponseType() {
-            result.hasResponseType = false;
-            result.responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType.CAPABILITY_EXCHANGE;
-            return this;
-          }
-
-          public Builder clone() {
-            return create().mergeFrom(result);
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog getAddLog() {
-            return result.getAddLog();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch getAddLogBranch() {
-            return result.getAddLogBranch();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange getCapabilityExchange() {
-            return result.getCapabilityExchange();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse getDefaultInstanceForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance();
-          }
-
-          public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDescriptor();
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType getResponseType() {
-            return result.getResponseType();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLog
-          // addLog = 3;
-          public boolean hasAddLog() {
-            return result.hasAddLog();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLogBranch
-          // addLogBranch = 4;
-          public boolean hasAddLogBranch() {
-            return result.hasAddLogBranch();
-          }
-
-          // optional
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange
-          // capabilityExchange = 2;
-          public boolean hasCapabilityExchange() {
-            return result.hasCapabilityExchange();
-          }
-
-          // required
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.ResponseType
-          // responseType = 1;
-          public boolean hasResponseType() {
-            return result.hasResponseType();
-          }
-
-          public boolean isInitialized() {
-            return result.isInitialized();
-          }
-
-          public Builder mergeAddLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog value) {
-            if (result.hasAddLog()
-                && result.addLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance()) {
-              result.addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.newBuilder(
-                  result.addLog_).mergeFrom(value).buildPartial();
+          
+          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse) {
+              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse)other);
             } else {
-              result.addLog_ = value;
+              super.mergeFrom(other);
+              return this;
             }
-            result.hasAddLog = true;
+          }
+          
+          public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse other) {
+            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance()) return this;
+            if (other.hasResponseType()) {
+              setResponseType(other.getResponseType());
+            }
+            if (other.hasCapabilityExchange()) {
+              mergeCapabilityExchange(other.getCapabilityExchange());
+            }
+            if (other.hasAddLog()) {
+              mergeAddLog(other.getAddLog());
+            }
+            if (other.hasAddLogBranch()) {
+              mergeAddLogBranch(other.getAddLogBranch());
+            }
+            this.mergeUnknownFields(other.getUnknownFields());
             return this;
           }
-
-          public Builder mergeAddLogBranch(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch value) {
-            if (result.hasAddLogBranch()
-                && result.addLogBranch_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance()) {
-              result.addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.newBuilder(
-                  result.addLogBranch_).mergeFrom(value).buildPartial();
-            } else {
-              result.addLogBranch_ = value;
-            }
-            result.hasAddLogBranch = true;
-            return this;
-          }
-
-          public Builder mergeCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange value) {
-            if (result.hasCapabilityExchange()
-                && result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance()) {
-              result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.newBuilder(
-                  result.capabilityExchange_).mergeFrom(value).buildPartial();
-            } else {
-              result.capabilityExchange_ = value;
-            }
-            result.hasCapabilityExchange = true;
-            return this;
-          }
-
+          
           public Builder mergeFrom(
               com.google.gwt.dev.protobuf.CodedInputStream input,
               com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
               throws java.io.IOException {
-            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+              com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                this.getUnknownFields());
             while (true) {
               int tag = input.readTag();
               switch (tag) {
@@ -9318,7 +7705,7 @@
                   return this;
                 default: {
                   if (!parseUnknownField(input, unknownFields,
-                      extensionRegistry, tag)) {
+                                         extensionRegistry, tag)) {
                     this.setUnknownFields(unknownFields.build());
                     return this;
                   }
@@ -9364,89 +7751,16 @@
               }
             }
           }
-
-          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse) {
-              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse) other);
-            } else {
-              super.mergeFrom(other);
-              return this;
-            }
+          
+          
+          // required .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.ResponseType responseType = 1;
+          public boolean hasResponseType() {
+            return result.hasResponseType();
           }
-
-          public Builder mergeFrom(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse other) {
-            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance())
-              return this;
-            if (other.hasResponseType()) {
-              setResponseType(other.getResponseType());
-            }
-            if (other.hasCapabilityExchange()) {
-              mergeCapabilityExchange(other.getCapabilityExchange());
-            }
-            if (other.hasAddLog()) {
-              mergeAddLog(other.getAddLog());
-            }
-            if (other.hasAddLogBranch()) {
-              mergeAddLogBranch(other.getAddLogBranch());
-            }
-            this.mergeUnknownFields(other.getUnknownFields());
-            return this;
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType getResponseType() {
+            return result.getResponseType();
           }
-
-          public Builder setAddLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasAddLog = true;
-            result.addLog_ = value;
-            return this;
-          }
-
-          public Builder setAddLog(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.Builder builderForValue) {
-            result.hasAddLog = true;
-            result.addLog_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setAddLogBranch(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasAddLogBranch = true;
-            result.addLogBranch_ = value;
-            return this;
-          }
-
-          public Builder setAddLogBranch(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.Builder builderForValue) {
-            result.hasAddLogBranch = true;
-            result.addLogBranch_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange value) {
-            if (value == null) {
-              throw new NullPointerException();
-            }
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = value;
-            return this;
-          }
-
-          public Builder setCapabilityExchange(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Builder builderForValue) {
-            result.hasCapabilityExchange = true;
-            result.capabilityExchange_ = builderForValue.build();
-            return this;
-          }
-
-          public Builder setResponseType(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType value) {
+          public Builder setResponseType(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType value) {
             if (value == null) {
               throw new NullPointerException();
             }
@@ -9454,296 +7768,463 @@
             result.responseType_ = value;
             return this;
           }
-
-          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse internalGetResult() {
-            return result;
+          public Builder clearResponseType() {
+            result.hasResponseType = false;
+            result.responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType.CAPABILITY_EXCHANGE;
+            return this;
           }
-
-          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse buildParsed()
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            if (!isInitialized()) {
-              throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange capabilityExchange = 2;
+          public boolean hasCapabilityExchange() {
+            return result.hasCapabilityExchange();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange getCapabilityExchange() {
+            return result.getCapabilityExchange();
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange value) {
+            if (value == null) {
+              throw new NullPointerException();
             }
-            return buildPartial();
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = value;
+            return this;
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Builder builderForValue) {
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange value) {
+            if (result.hasCapabilityExchange() &&
+                result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance()) {
+              result.capabilityExchange_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.newBuilder(result.capabilityExchange_).mergeFrom(value).buildPartial();
+            } else {
+              result.capabilityExchange_ = value;
+            }
+            result.hasCapabilityExchange = true;
+            return this;
+          }
+          public Builder clearCapabilityExchange() {
+            result.hasCapabilityExchange = false;
+            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLog addLog = 3;
+          public boolean hasAddLog() {
+            return result.hasAddLog();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog getAddLog() {
+            return result.getAddLog();
+          }
+          public Builder setAddLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasAddLog = true;
+            result.addLog_ = value;
+            return this;
+          }
+          public Builder setAddLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.Builder builderForValue) {
+            result.hasAddLog = true;
+            result.addLog_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeAddLog(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog value) {
+            if (result.hasAddLog() &&
+                result.addLog_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance()) {
+              result.addLog_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.newBuilder(result.addLog_).mergeFrom(value).buildPartial();
+            } else {
+              result.addLog_ = value;
+            }
+            result.hasAddLog = true;
+            return this;
+          }
+          public Builder clearAddLog() {
+            result.hasAddLog = false;
+            result.addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLogBranch addLogBranch = 4;
+          public boolean hasAddLogBranch() {
+            return result.hasAddLogBranch();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch getAddLogBranch() {
+            return result.getAddLogBranch();
+          }
+          public Builder setAddLogBranch(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasAddLogBranch = true;
+            result.addLogBranch_ = value;
+            return this;
+          }
+          public Builder setAddLogBranch(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.Builder builderForValue) {
+            result.hasAddLogBranch = true;
+            result.addLogBranch_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeAddLogBranch(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch value) {
+            if (result.hasAddLogBranch() &&
+                result.addLogBranch_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance()) {
+              result.addLogBranch_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.newBuilder(result.addLogBranch_).mergeFrom(value).buildPartial();
+            } else {
+              result.addLogBranch_ = value;
+            }
+            result.hasAddLogBranch = true;
+            return this;
+          }
+          public Builder clearAddLogBranch() {
+            result.hasAddLogBranch = false;
+            result.addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance();
+            return this;
           }
         }
-
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+        }
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+        }
+      }
+      
+      public static final class DevModeResponse extends
+          com.google.gwt.dev.protobuf.GeneratedMessage {
+        // Use DevModeResponse.newBuilder() to construct.
+        private DevModeResponse() {}
+        
+        private static final DevModeResponse defaultInstance = new DevModeResponse();
+        public static DevModeResponse getDefaultInstance() {
+          return defaultInstance;
+        }
+        
+        public DevModeResponse getDefaultInstanceForType() {
+          return defaultInstance;
+        }
+        
+        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+            getDescriptor() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor;
+        }
+        
+        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+            internalGetFieldAccessorTable() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_fieldAccessorTable;
+        }
+        
+        public enum ResponseType
+            implements com.google.gwt.dev.protobuf.ProtocolMessageEnum {
+          CAPABILITY_EXCHANGE(0, 0),
+          RESTART_WEB_SERVER(1, 1),
+          ;
+          
+          
+          public final int getNumber() { return value; }
+          
+          public static ResponseType valueOf(int value) {
+            switch (value) {
+              case 0: return CAPABILITY_EXCHANGE;
+              case 1: return RESTART_WEB_SERVER;
+              default: return null;
+            }
+          }
+          
+          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>
+              internalGetValueMap() {
+            return internalValueMap;
+          }
+          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>
+              internalValueMap =
+                new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>() {
+                  public ResponseType findValueByNumber(int number) {
+                    return ResponseType.valueOf(number)
+          ;        }
+                };
+          
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor
+              getValueDescriptor() {
+            return getDescriptor().getValues().get(index);
+          }
+          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptorForType() {
+            return getDescriptor();
+          }
+          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDescriptor().getEnumTypes().get(0);
+          }
+          
+          private static final ResponseType[] VALUES = {
+            CAPABILITY_EXCHANGE, RESTART_WEB_SERVER, 
+          };
+          public static ResponseType valueOf(
+              com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
+            if (desc.getType() != getDescriptor()) {
+              throw new java.lang.IllegalArgumentException(
+                "EnumValueDescriptor is not for this type.");
+            }
+            return VALUES[desc.getIndex()];
+          }
+          private final int index;
+          private final int value;
+          private ResponseType(int index, int value) {
+            this.index = index;
+            this.value = value;
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+        }
+        
         public static final class CapabilityExchange extends
             com.google.gwt.dev.protobuf.GeneratedMessage {
-          public static final class Builder extends
-              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
-            private static Builder create() {
-              Builder builder = new Builder();
-              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange();
-              return builder;
+          // Use CapabilityExchange.newBuilder() to construct.
+          private CapabilityExchange() {}
+          
+          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
+          public static CapabilityExchange getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public CapabilityExchange getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_fieldAccessorTable;
+          }
+          
+          public static final class Capability extends
+              com.google.gwt.dev.protobuf.GeneratedMessage {
+            // Use Capability.newBuilder() to construct.
+            private Capability() {}
+            
+            private static final Capability defaultInstance = new Capability();
+            public static Capability getDefaultInstance() {
+              return defaultInstance;
             }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange result;
-
-            // Construct using
-            // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.newBuilder()
-            private Builder() {
+            
+            public Capability getDefaultInstanceForType() {
+              return defaultInstance;
             }
-
-            public Builder addAllCapabilities(
-                java.lang.Iterable<? extends com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> values) {
-              if (result.capabilities_.isEmpty()) {
-                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
+            
+            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptor() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor;
+            }
+            
+            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+                internalGetFieldAccessorTable() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_fieldAccessorTable;
+            }
+            
+            // required .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType capability = 1;
+            public static final int CAPABILITY_FIELD_NUMBER = 1;
+            private boolean hasCapability;
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
+            public boolean hasCapability() { return hasCapability; }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getCapability() { return capability_; }
+            
+            public final boolean isInitialized() {
+              if (!hasCapability) return false;
+              return true;
+            }
+            
+            public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                                throws java.io.IOException {
+              if (hasCapability()) {
+                output.writeEnum(1, getCapability().getNumber());
               }
-              super.addAll(values, result.capabilities_);
-              return this;
+              getUnknownFields().writeTo(output);
             }
-
-            public Builder addCapabilities(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability value) {
-              if (value == null) {
-                throw new NullPointerException();
+            
+            private int memoizedSerializedSize = -1;
+            public int getSerializedSize() {
+              int size = memoizedSerializedSize;
+              if (size != -1) return size;
+            
+              size = 0;
+              if (hasCapability()) {
+                size += com.google.gwt.dev.protobuf.CodedOutputStream
+                  .computeEnumSize(1, getCapability().getNumber());
               }
-              if (result.capabilities_.isEmpty()) {
-                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
-              }
-              result.capabilities_.add(value);
-              return this;
+              size += getUnknownFields().getSerializedSize();
+              memoizedSerializedSize = size;
+              return size;
             }
-
-            public Builder addCapabilities(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder builderForValue) {
-              if (result.capabilities_.isEmpty()) {
-                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
-              }
-              result.capabilities_.add(builderForValue.build());
-              return this;
+            
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange build() {
-              if (result != null && !isInitialized()) {
-                throw newUninitializedMessageException(result);
-              }
-              return buildPartial();
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
+                com.google.gwt.dev.protobuf.ByteString data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange buildPartial() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "build() has already been called on this Builder.");
-              }
-              if (result.capabilities_ != java.util.Collections.EMPTY_LIST) {
-                result.capabilities_ = java.util.Collections.unmodifiableList(result.capabilities_);
-              }
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange returnMe = result;
-              result = null;
-              return returnMe;
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(byte[] data)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data).buildParsed();
             }
-
-            public Builder clear() {
-              if (result == null) {
-                throw new IllegalStateException(
-                    "Cannot call clear() after build().");
-              }
-              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange();
-              return this;
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
+                byte[] data,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              return newBuilder().mergeFrom(data, extensionRegistry)
+                       .buildParsed();
             }
-
-            public Builder clearCapabilities() {
-              result.capabilities_ = java.util.Collections.emptyList();
-              return this;
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
             }
-
-            public Builder clone() {
-              return create().mergeFrom(result);
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability getCapabilities(
-                int index) {
-              return result.getCapabilities(index);
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseDelimitedFrom(java.io.InputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input).buildParsed();
             }
-
-            public int getCapabilitiesCount() {
-              return result.getCapabilitiesCount();
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseDelimitedFrom(
+                java.io.InputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                       .buildParsed();
             }
-
-            // repeated
-            // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange.Capability
-            // capabilities = 2;
-            public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> getCapabilitiesList() {
-              return java.util.Collections.unmodifiableList(result.capabilities_);
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input)
+                throws java.io.IOException {
+              return newBuilder().mergeFrom(input).buildParsed();
             }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange getDefaultInstanceForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance();
-            }
-
-            public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDescriptor();
-            }
-
-            public boolean isInitialized() {
-              return result.isInitialized();
-            }
-
-            public Builder mergeFrom(
+            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability parseFrom(
                 com.google.gwt.dev.protobuf.CodedInputStream input,
                 com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                 throws java.io.IOException {
-              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
-              while (true) {
-                int tag = input.readTag();
-                switch (tag) {
-                  case 0:
-                    this.setUnknownFields(unknownFields.build());
-                    return this;
-                  default: {
-                    if (!parseUnknownField(input, unknownFields,
-                        extensionRegistry, tag)) {
-                      this.setUnknownFields(unknownFields.build());
-                      return this;
-                    }
-                    break;
-                  }
-                  case 18: {
-                    com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.newBuilder();
-                    input.readMessage(subBuilder, extensionRegistry);
-                    addCapabilities(subBuilder.buildPartial());
-                    break;
-                  }
-                }
-              }
+              return newBuilder().mergeFrom(input, extensionRegistry)
+                       .buildParsed();
             }
-
-            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange) {
-                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange) other);
-              } else {
-                super.mergeFrom(other);
-                return this;
-              }
+            
+            public static Builder newBuilder() { return Builder.create(); }
+            public Builder newBuilderForType() { return newBuilder(); }
+            public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability prototype) {
+              return newBuilder().mergeFrom(prototype);
             }
-
-            public Builder mergeFrom(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange other) {
-              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance())
-                return this;
-              if (!other.capabilities_.isEmpty()) {
-                if (result.capabilities_.isEmpty()) {
-                  result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability>();
-                }
-                result.capabilities_.addAll(other.capabilities_);
-              }
-              this.mergeUnknownFields(other.getUnknownFields());
-              return this;
-            }
-
-            public Builder setCapabilities(
-                int index,
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability value) {
-              if (value == null) {
-                throw new NullPointerException();
-              }
-              result.capabilities_.set(index, value);
-              return this;
-            }
-
-            public Builder setCapabilities(
-                int index,
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder builderForValue) {
-              result.capabilities_.set(index, builderForValue.build());
-              return this;
-            }
-
-            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange internalGetResult() {
-              return result;
-            }
-
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange buildParsed()
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              if (!isInitialized()) {
-                throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-              }
-              return buildPartial();
-            }
-          }
-
-          public static final class Capability extends
-              com.google.gwt.dev.protobuf.GeneratedMessage {
+            public Builder toBuilder() { return newBuilder(this); }
+            
             public static final class Builder extends
                 com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability result;
+              
+              // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.newBuilder()
+              private Builder() {}
+              
               private static Builder create() {
                 Builder builder = new Builder();
-                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability();
+                builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability();
                 return builder;
               }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability result;
-
-              // Construct using
-              // com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.newBuilder()
-              private Builder() {
+              
+              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability internalGetResult() {
+                return result;
               }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability build() {
+              
+              public Builder clear() {
+                if (result == null) {
+                  throw new IllegalStateException(
+                    "Cannot call clear() after build().");
+                }
+                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability();
+                return this;
+              }
+              
+              public Builder clone() {
+                return create().mergeFrom(result);
+              }
+              
+              public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                  getDescriptorForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.getDescriptor();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability getDefaultInstanceForType() {
+                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.getDefaultInstance();
+              }
+              
+              public boolean isInitialized() {
+                return result.isInitialized();
+              }
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability build() {
                 if (result != null && !isInitialized()) {
                   throw newUninitializedMessageException(result);
                 }
                 return buildPartial();
               }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability buildPartial() {
+              
+              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability buildParsed()
+                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+                if (!isInitialized()) {
+                  throw newUninitializedMessageException(
+                    result).asInvalidProtocolBufferException();
+                }
+                return buildPartial();
+              }
+              
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability buildPartial() {
                 if (result == null) {
                   throw new IllegalStateException(
-                      "build() has already been called on this Builder.");
+                    "build() has already been called on this Builder.");
                 }
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability returnMe = result;
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability returnMe = result;
                 result = null;
                 return returnMe;
               }
-
-              public Builder clear() {
-                if (result == null) {
-                  throw new IllegalStateException(
-                      "Cannot call clear() after build().");
+              
+              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability) {
+                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability)other);
+                } else {
+                  super.mergeFrom(other);
+                  return this;
                 }
-                result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability();
+              }
+              
+              public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability other) {
+                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.getDefaultInstance()) return this;
+                if (other.hasCapability()) {
+                  setCapability(other.getCapability());
+                }
+                this.mergeUnknownFields(other.getUnknownFields());
                 return this;
               }
-
-              public Builder clearCapability() {
-                result.hasCapability = false;
-                result.capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
-                return this;
-              }
-
-              public Builder clone() {
-                return create().mergeFrom(result);
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getCapability() {
-                return result.getCapability();
-              }
-
-              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability getDefaultInstanceForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.getDefaultInstance();
-              }
-
-              public com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptorForType() {
-                return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.getDescriptor();
-              }
-
-              // required
-              // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType
-              // capability = 1;
-              public boolean hasCapability() {
-                return result.hasCapability();
-              }
-
-              public boolean isInitialized() {
-                return result.isInitialized();
-              }
-
+              
               public Builder mergeFrom(
                   com.google.gwt.dev.protobuf.CodedInputStream input,
                   com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
                   throws java.io.IOException {
-                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields = com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(this.getUnknownFields());
+                com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                  com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                    this.getUnknownFields());
                 while (true) {
                   int tag = input.readTag();
                   switch (tag) {
@@ -9752,7 +8233,7 @@
                       return this;
                     default: {
                       if (!parseUnknownField(input, unknownFields,
-                          extensionRegistry, tag)) {
+                                             extensionRegistry, tag)) {
                         this.setUnknownFields(unknownFields.build());
                         return this;
                       }
@@ -9760,7 +8241,7 @@
                     }
                     case 8: {
                       int rawValue = input.readEnum();
-                      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.valueOf(rawValue);
+                      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.valueOf(rawValue);
                       if (value == null) {
                         unknownFields.mergeVarintField(1, rawValue);
                       } else {
@@ -9771,29 +8252,16 @@
                   }
                 }
               }
-
-              public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
-                if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability) {
-                  return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability) other);
-                } else {
-                  super.mergeFrom(other);
-                  return this;
-                }
+              
+              
+              // required .com.google.gwt.dev.shell.remoteui.Message.Request.DevModeRequest.RequestType capability = 1;
+              public boolean hasCapability() {
+                return result.hasCapability();
               }
-
-              public Builder mergeFrom(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability other) {
-                if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.getDefaultInstance())
-                  return this;
-                if (other.hasCapability()) {
-                  setCapability(other.getCapability());
-                }
-                this.mergeUnknownFields(other.getUnknownFields());
-                return this;
+              public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType getCapability() {
+                return result.getCapability();
               }
-
-              public Builder setCapability(
-                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType value) {
+              public Builder setCapability(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType value) {
                 if (value == null) {
                   throw new NullPointerException();
                 }
@@ -9801,841 +8269,959 @@
                 result.capability_ = value;
                 return this;
               }
-
-              protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability internalGetResult() {
-                return result;
-              }
-
-              private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability buildParsed()
-                  throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-                if (!isInitialized()) {
-                  throw newUninitializedMessageException(result).asInvalidProtocolBufferException();
-                }
-                return buildPartial();
+              public Builder clearCapability() {
+                result.hasCapability = false;
+                result.capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RequestType.CAPABILITY_EXCHANGE;
+                return this;
               }
             }
-
-            private static final Capability defaultInstance = new Capability();
-            // required
-            // .com.google.gwt.dev.shell.remoteui.Message.Request.ViewerRequest.RequestType
-            // capability = 1;
-            public static final int CAPABILITY_FIELD_NUMBER = 1;
-
+            
             static {
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
             }
-
+            
             static {
               com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
             }
-
-            public static Capability getDefaultInstance() {
-              return defaultInstance;
-            }
-
-            public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor;
-            }
-
-            public static Builder newBuilder() {
-              return Builder.create();
-            }
-
-            public static Builder newBuilder(
-                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability prototype) {
-              return newBuilder().mergeFrom(prototype);
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseDelimitedFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseDelimitedFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                byte[] data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                byte[] data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.ByteString data,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-              return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                com.google.gwt.dev.protobuf.CodedInputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                java.io.InputStream input) throws java.io.IOException {
-              return newBuilder().mergeFrom(input).buildParsed();
-            }
-
-            public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability parseFrom(
-                java.io.InputStream input,
-                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-                throws java.io.IOException {
-              return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-            }
-
-            private boolean hasCapability;
-            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType capability_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType.CAPABILITY_EXCHANGE;
-            private int memoizedSerializedSize = -1;
-
-            // Use Capability.newBuilder() to construct.
-            private Capability() {
-            }
-
-            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.RequestType getCapability() {
-              return capability_;
-            }
-
-            public Capability getDefaultInstanceForType() {
-              return defaultInstance;
-            }
-
-            public int getSerializedSize() {
-              int size = memoizedSerializedSize;
-              if (size != -1)
-                return size;
-
-              size = 0;
-              if (hasCapability()) {
-                size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-                    1, getCapability().getNumber());
-              }
-              size += getUnknownFields().getSerializedSize();
-              memoizedSerializedSize = size;
-              return size;
-            }
-
-            public boolean hasCapability() {
-              return hasCapability;
-            }
-
-            public final boolean isInitialized() {
-              if (!hasCapability)
-                return false;
-              return true;
-            }
-
-            public Builder newBuilderForType() {
-              return newBuilder();
-            }
-
-            public Builder toBuilder() {
-              return newBuilder(this);
-            }
-
-            public void writeTo(
-                com.google.gwt.dev.protobuf.CodedOutputStream output)
-                throws java.io.IOException {
-              if (hasCapability()) {
-                output.writeEnum(1, getCapability().getNumber());
-              }
-              getUnknownFields().writeTo(output);
-            }
-
-            protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_fieldAccessorTable;
-            }
           }
-
-          private static final CapabilityExchange defaultInstance = new CapabilityExchange();
-
-          // repeated
-          // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange.Capability
-          // capabilities = 2;
+          
+          // repeated .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange.Capability capabilities = 2;
           public static final int CAPABILITIES_FIELD_NUMBER = 2;
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-          }
-
-          static {
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-          }
-
-          public static CapabilityExchange getDefaultInstance() {
-            return defaultInstance;
-          }
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor;
-          }
-
-          public static Builder newBuilder() {
-            return Builder.create();
-          }
-
-          public static Builder newBuilder(
-              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange prototype) {
-            return newBuilder().mergeFrom(prototype);
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseDelimitedFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              byte[] data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              byte[] data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.ByteString data,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-            return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              com.google.gwt.dev.protobuf.CodedInputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              java.io.InputStream input) throws java.io.IOException {
-            return newBuilder().mergeFrom(input).buildParsed();
-          }
-
-          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange parseFrom(
-              java.io.InputStream input,
-              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-              throws java.io.IOException {
-            return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-          }
-
-          private java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> capabilities_ = java.util.Collections.emptyList();
-          private int memoizedSerializedSize = -1;
-
-          // Use CapabilityExchange.newBuilder() to construct.
-          private CapabilityExchange() {
-          }
-
-          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability getCapabilities(
-              int index) {
-            return capabilities_.get(index);
-          }
-
-          public int getCapabilitiesCount() {
-            return capabilities_.size();
-          }
-
-          public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability> getCapabilitiesList() {
+          private java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> capabilities_ =
+            java.util.Collections.emptyList();
+          public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> getCapabilitiesList() {
             return capabilities_;
           }
-
-          public CapabilityExchange getDefaultInstanceForType() {
-            return defaultInstance;
+          public int getCapabilitiesCount() { return capabilities_.size(); }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability getCapabilities(int index) {
+            return capabilities_.get(index);
           }
-
+          
+          public final boolean isInitialized() {
+            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
+              if (!element.isInitialized()) return false;
+            }
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
+              output.writeMessage(2, element);
+            }
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
           public int getSerializedSize() {
             int size = memoizedSerializedSize;
-            if (size != -1)
-              return size;
-
+            if (size != -1) return size;
+          
             size = 0;
-            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
-              size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                  2, element);
+            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
+              size += com.google.gwt.dev.protobuf.CodedOutputStream
+                .computeMessageSize(2, element);
             }
             size += getUnknownFields().getSerializedSize();
             memoizedSerializedSize = size;
             return size;
           }
-
-          public final boolean isInitialized() {
-            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
-              if (!element.isInitialized())
-                return false;
-            }
-            return true;
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public Builder newBuilderForType() {
-            return newBuilder();
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
           }
-
-          public Builder toBuilder() {
-            return newBuilder(this);
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
           }
-
-          public void writeTo(
-              com.google.gwt.dev.protobuf.CodedOutputStream output)
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(java.io.InputStream input)
               throws java.io.IOException {
-            for (com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability element : getCapabilitiesList()) {
-              output.writeMessage(2, element);
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange();
+              return builder;
             }
-            getUnknownFields().writeTo(output);
-          }
-
-          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_fieldAccessorTable;
-          }
-        }
-
-        public enum ResponseType implements
-            com.google.gwt.dev.protobuf.ProtocolMessageEnum {
-          CAPABILITY_EXCHANGE(0, 0), ADD_LOG(1, 1), ADD_LOG_BRANCH(2, 2), ;
-
-          private static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType> internalValueMap = new com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType>() {
-            public ResponseType findValueByNumber(int number) {
-              return ResponseType.valueOf(number);
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange internalGetResult() {
+              return result;
             }
-          };
-
-          private static final ResponseType[] VALUES = {
-              CAPABILITY_EXCHANGE, ADD_LOG, ADD_LOG_BRANCH,};
-
-          public static final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptor() {
-            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDescriptor().getEnumTypes().get(
-                0);
-          }
-
-          public static com.google.gwt.dev.protobuf.Internal.EnumLiteMap<ResponseType> internalGetValueMap() {
-            return internalValueMap;
-          }
-
-          public static ResponseType valueOf(
-              com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor desc) {
-            if (desc.getType() != getDescriptor()) {
-              throw new java.lang.IllegalArgumentException(
-                  "EnumValueDescriptor is not for this type.");
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange();
+              return this;
             }
-            return VALUES[desc.getIndex()];
-          }
-
-          public static ResponseType valueOf(int value) {
-            switch (value) {
-              case 0:
-                return CAPABILITY_EXCHANGE;
-              case 1:
-                return ADD_LOG;
-              case 2:
-                return ADD_LOG_BRANCH;
-              default:
-                return null;
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              if (result.capabilities_ != java.util.Collections.EMPTY_LIST) {
+                result.capabilities_ =
+                  java.util.Collections.unmodifiableList(result.capabilities_);
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance()) return this;
+              if (!other.capabilities_.isEmpty()) {
+                if (result.capabilities_.isEmpty()) {
+                  result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
+                }
+                result.capabilities_.addAll(other.capabilities_);
+              }
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                  case 18: {
+                    com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.newBuilder();
+                    input.readMessage(subBuilder, extensionRegistry);
+                    addCapabilities(subBuilder.buildPartial());
+                    break;
+                  }
+                }
+              }
+            }
+            
+            
+            // repeated .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange.Capability capabilities = 2;
+            public java.util.List<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> getCapabilitiesList() {
+              return java.util.Collections.unmodifiableList(result.capabilities_);
+            }
+            public int getCapabilitiesCount() {
+              return result.getCapabilitiesCount();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability getCapabilities(int index) {
+              return result.getCapabilities(index);
+            }
+            public Builder setCapabilities(int index, com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability value) {
+              if (value == null) {
+                throw new NullPointerException();
+              }
+              result.capabilities_.set(index, value);
+              return this;
+            }
+            public Builder setCapabilities(int index, com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder builderForValue) {
+              result.capabilities_.set(index, builderForValue.build());
+              return this;
+            }
+            public Builder addCapabilities(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability value) {
+              if (value == null) {
+                throw new NullPointerException();
+              }
+              if (result.capabilities_.isEmpty()) {
+                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
+              }
+              result.capabilities_.add(value);
+              return this;
+            }
+            public Builder addCapabilities(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder builderForValue) {
+              if (result.capabilities_.isEmpty()) {
+                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
+              }
+              result.capabilities_.add(builderForValue.build());
+              return this;
+            }
+            public Builder addAllCapabilities(
+                java.lang.Iterable<? extends com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability> values) {
+              if (result.capabilities_.isEmpty()) {
+                result.capabilities_ = new java.util.ArrayList<com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability>();
+              }
+              super.addAll(values, result.capabilities_);
+              return this;
+            }
+            public Builder clearCapabilities() {
+              result.capabilities_ = java.util.Collections.emptyList();
+              return this;
             }
           }
-
-          private final int index;
-
-          private final int value;
+          
           static {
             com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
           }
-
-          private ResponseType(int index, int value) {
-            this.index = index;
-            this.value = value;
-          }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumDescriptor getDescriptorForType() {
-            return getDescriptor();
-          }
-
-          public final int getNumber() {
-            return value;
-          }
-
-          public final com.google.gwt.dev.protobuf.Descriptors.EnumValueDescriptor getValueDescriptor() {
-            return getDescriptor().getValues().get(index);
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
           }
         }
-
-        private static final ViewerResponse defaultInstance = new ViewerResponse();
-
-        // required
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.ResponseType
-        // responseType = 1;
+        
+        public static final class RestartWebServer extends
+            com.google.gwt.dev.protobuf.GeneratedMessage {
+          // Use RestartWebServer.newBuilder() to construct.
+          private RestartWebServer() {}
+          
+          private static final RestartWebServer defaultInstance = new RestartWebServer();
+          public static RestartWebServer getDefaultInstance() {
+            return defaultInstance;
+          }
+          
+          public RestartWebServer getDefaultInstanceForType() {
+            return defaultInstance;
+          }
+          
+          public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptor() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor;
+          }
+          
+          protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+              internalGetFieldAccessorTable() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_fieldAccessorTable;
+          }
+          
+          public final boolean isInitialized() {
+            return true;
+          }
+          
+          public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
+                              throws java.io.IOException {
+            getUnknownFields().writeTo(output);
+          }
+          
+          private int memoizedSerializedSize = -1;
+          public int getSerializedSize() {
+            int size = memoizedSerializedSize;
+            if (size != -1) return size;
+          
+            size = 0;
+            size += getUnknownFields().getSerializedSize();
+            memoizedSerializedSize = size;
+            return size;
+          }
+          
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.ByteString data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(byte[] data)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
+              byte[] data,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            return newBuilder().mergeFrom(data, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseDelimitedFrom(java.io.InputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseDelimitedFrom(
+              java.io.InputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input).buildParsed();
+          }
+          public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer parseFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            return newBuilder().mergeFrom(input, extensionRegistry)
+                     .buildParsed();
+          }
+          
+          public static Builder newBuilder() { return Builder.create(); }
+          public Builder newBuilderForType() { return newBuilder(); }
+          public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer prototype) {
+            return newBuilder().mergeFrom(prototype);
+          }
+          public Builder toBuilder() { return newBuilder(this); }
+          
+          public static final class Builder extends
+              com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer result;
+            
+            // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.newBuilder()
+            private Builder() {}
+            
+            private static Builder create() {
+              Builder builder = new Builder();
+              builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer();
+              return builder;
+            }
+            
+            protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer internalGetResult() {
+              return result;
+            }
+            
+            public Builder clear() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "Cannot call clear() after build().");
+              }
+              result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer();
+              return this;
+            }
+            
+            public Builder clone() {
+              return create().mergeFrom(result);
+            }
+            
+            public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+                getDescriptorForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDescriptor();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer getDefaultInstanceForType() {
+              return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance();
+            }
+            
+            public boolean isInitialized() {
+              return result.isInitialized();
+            }
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer build() {
+              if (result != null && !isInitialized()) {
+                throw newUninitializedMessageException(result);
+              }
+              return buildPartial();
+            }
+            
+            private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer buildParsed()
+                throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+              if (!isInitialized()) {
+                throw newUninitializedMessageException(
+                  result).asInvalidProtocolBufferException();
+              }
+              return buildPartial();
+            }
+            
+            public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer buildPartial() {
+              if (result == null) {
+                throw new IllegalStateException(
+                  "build() has already been called on this Builder.");
+              }
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer returnMe = result;
+              result = null;
+              return returnMe;
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+              if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer) {
+                return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer)other);
+              } else {
+                super.mergeFrom(other);
+                return this;
+              }
+            }
+            
+            public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer other) {
+              if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance()) return this;
+              this.mergeUnknownFields(other.getUnknownFields());
+              return this;
+            }
+            
+            public Builder mergeFrom(
+                com.google.gwt.dev.protobuf.CodedInputStream input,
+                com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+                throws java.io.IOException {
+              com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+                com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                  this.getUnknownFields());
+              while (true) {
+                int tag = input.readTag();
+                switch (tag) {
+                  case 0:
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  default: {
+                    if (!parseUnknownField(input, unknownFields,
+                                           extensionRegistry, tag)) {
+                      this.setUnknownFields(unknownFields.build());
+                      return this;
+                    }
+                    break;
+                  }
+                }
+              }
+            }
+            
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+          }
+          
+          static {
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
+          }
+        }
+        
+        // required .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.ResponseType responseType = 1;
         public static final int RESPONSETYPE_FIELD_NUMBER = 1;
-
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLogBranch
-        // addLogBranch = 4;
-        public static final int ADDLOGBRANCH_FIELD_NUMBER = 4;
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-        }
-
-        static {
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-        }
-
-        public static ViewerResponse getDefaultInstance() {
-          return defaultInstance;
-        }
-
-        public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor;
-        }
-
-        public static Builder newBuilder() {
-          return Builder.create();
-        }
-
-        public static Builder newBuilder(
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse prototype) {
-          return newBuilder().mergeFrom(prototype);
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseDelimitedFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseDelimitedFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            byte[] data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            byte[] data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            com.google.gwt.dev.protobuf.ByteString data,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-          return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            com.google.gwt.dev.protobuf.CodedInputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            java.io.InputStream input) throws java.io.IOException {
-          return newBuilder().mergeFrom(input).buildParsed();
-        }
-
-        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse parseFrom(
-            java.io.InputStream input,
-            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-            throws java.io.IOException {
-          return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-        }
-
         private boolean hasResponseType;
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType.CAPABILITY_EXCHANGE;
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.CapabilityExchange
-        // capabilityExchange = 2;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType.CAPABILITY_EXCHANGE;
+        public boolean hasResponseType() { return hasResponseType; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType getResponseType() { return responseType_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange capabilityExchange = 2;
         public static final int CAPABILITYEXCHANGE_FIELD_NUMBER = 2;
         private boolean hasCapabilityExchange;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.getDefaultInstance();
-        // optional
-        // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse.AddLog
-        // addLog = 3;
-        public static final int ADDLOG_FIELD_NUMBER = 3;
-
-        private boolean hasAddLog;
-
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog addLog_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.getDefaultInstance();
-
-        private boolean hasAddLogBranch;
-        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch addLogBranch_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.getDefaultInstance();
-
-        private int memoizedSerializedSize = -1;
-
-        // Use ViewerResponse.newBuilder() to construct.
-        private ViewerResponse() {
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog getAddLog() {
-          return addLog_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch getAddLogBranch() {
-          return addLogBranch_;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange getCapabilityExchange() {
-          return capabilityExchange_;
-        }
-
-        public ViewerResponse getDefaultInstanceForType() {
-          return defaultInstance;
-        }
-
-        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.ResponseType getResponseType() {
-          return responseType_;
-        }
-
-        public int getSerializedSize() {
-          int size = memoizedSerializedSize;
-          if (size != -1)
-            return size;
-
-          size = 0;
-          if (hasResponseType()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-                1, getResponseType().getNumber());
-          }
-          if (hasCapabilityExchange()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                2, getCapabilityExchange());
-          }
-          if (hasAddLog()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                3, getAddLog());
-          }
-          if (hasAddLogBranch()) {
-            size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-                4, getAddLogBranch());
-          }
-          size += getUnknownFields().getSerializedSize();
-          memoizedSerializedSize = size;
-          return size;
-        }
-
-        public boolean hasAddLog() {
-          return hasAddLog;
-        }
-
-        public boolean hasAddLogBranch() {
-          return hasAddLogBranch;
-        }
-
-        public boolean hasCapabilityExchange() {
-          return hasCapabilityExchange;
-        }
-
-        public boolean hasResponseType() {
-          return hasResponseType;
-        }
-
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance();
+        public boolean hasCapabilityExchange() { return hasCapabilityExchange; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange getCapabilityExchange() { return capabilityExchange_; }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.RestartWebServer restartWebServer = 3;
+        public static final int RESTARTWEBSERVER_FIELD_NUMBER = 3;
+        private boolean hasRestartWebServer;
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance();
+        public boolean hasRestartWebServer() { return hasRestartWebServer; }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer getRestartWebServer() { return restartWebServer_; }
+        
         public final boolean isInitialized() {
-          if (!hasResponseType)
-            return false;
+          if (!hasResponseType) return false;
           if (hasCapabilityExchange()) {
-            if (!getCapabilityExchange().isInitialized())
-              return false;
-          }
-          if (hasAddLog()) {
-            if (!getAddLog().isInitialized())
-              return false;
-          }
-          if (hasAddLogBranch()) {
-            if (!getAddLogBranch().isInitialized())
-              return false;
+            if (!getCapabilityExchange().isInitialized()) return false;
           }
           return true;
         }
-
-        public Builder newBuilderForType() {
-          return newBuilder();
-        }
-
-        public Builder toBuilder() {
-          return newBuilder(this);
-        }
-
+        
         public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
-            throws java.io.IOException {
+                            throws java.io.IOException {
           if (hasResponseType()) {
             output.writeEnum(1, getResponseType().getNumber());
           }
           if (hasCapabilityExchange()) {
             output.writeMessage(2, getCapabilityExchange());
           }
-          if (hasAddLog()) {
-            output.writeMessage(3, getAddLog());
-          }
-          if (hasAddLogBranch()) {
-            output.writeMessage(4, getAddLogBranch());
+          if (hasRestartWebServer()) {
+            output.writeMessage(3, getRestartWebServer());
           }
           getUnknownFields().writeTo(output);
         }
-
-        protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_fieldAccessorTable;
+        
+        private int memoizedSerializedSize = -1;
+        public int getSerializedSize() {
+          int size = memoizedSerializedSize;
+          if (size != -1) return size;
+        
+          size = 0;
+          if (hasResponseType()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeEnumSize(1, getResponseType().getNumber());
+          }
+          if (hasCapabilityExchange()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(2, getCapabilityExchange());
+          }
+          if (hasRestartWebServer()) {
+            size += com.google.gwt.dev.protobuf.CodedOutputStream
+              .computeMessageSize(3, getRestartWebServer());
+          }
+          size += getUnknownFields().getSerializedSize();
+          memoizedSerializedSize = size;
+          return size;
+        }
+        
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
+            com.google.gwt.dev.protobuf.ByteString data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(byte[] data)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
+            byte[] data,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          return newBuilder().mergeFrom(data, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseDelimitedFrom(java.io.InputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseDelimitedFrom(
+            java.io.InputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input).buildParsed();
+        }
+        public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse parseFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          return newBuilder().mergeFrom(input, extensionRegistry)
+                   .buildParsed();
+        }
+        
+        public static Builder newBuilder() { return Builder.create(); }
+        public Builder newBuilderForType() { return newBuilder(); }
+        public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse prototype) {
+          return newBuilder().mergeFrom(prototype);
+        }
+        public Builder toBuilder() { return newBuilder(this); }
+        
+        public static final class Builder extends
+            com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse result;
+          
+          // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.newBuilder()
+          private Builder() {}
+          
+          private static Builder create() {
+            Builder builder = new Builder();
+            builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse();
+            return builder;
+          }
+          
+          protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse internalGetResult() {
+            return result;
+          }
+          
+          public Builder clear() {
+            if (result == null) {
+              throw new IllegalStateException(
+                "Cannot call clear() after build().");
+            }
+            result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse();
+            return this;
+          }
+          
+          public Builder clone() {
+            return create().mergeFrom(result);
+          }
+          
+          public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+              getDescriptorForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDescriptor();
+          }
+          
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse getDefaultInstanceForType() {
+            return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance();
+          }
+          
+          public boolean isInitialized() {
+            return result.isInitialized();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse build() {
+            if (result != null && !isInitialized()) {
+              throw newUninitializedMessageException(result);
+            }
+            return buildPartial();
+          }
+          
+          private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse buildParsed()
+              throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+            if (!isInitialized()) {
+              throw newUninitializedMessageException(
+                result).asInvalidProtocolBufferException();
+            }
+            return buildPartial();
+          }
+          
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse buildPartial() {
+            if (result == null) {
+              throw new IllegalStateException(
+                "build() has already been called on this Builder.");
+            }
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse returnMe = result;
+            result = null;
+            return returnMe;
+          }
+          
+          public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+            if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse) {
+              return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse)other);
+            } else {
+              super.mergeFrom(other);
+              return this;
+            }
+          }
+          
+          public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse other) {
+            if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance()) return this;
+            if (other.hasResponseType()) {
+              setResponseType(other.getResponseType());
+            }
+            if (other.hasCapabilityExchange()) {
+              mergeCapabilityExchange(other.getCapabilityExchange());
+            }
+            if (other.hasRestartWebServer()) {
+              mergeRestartWebServer(other.getRestartWebServer());
+            }
+            this.mergeUnknownFields(other.getUnknownFields());
+            return this;
+          }
+          
+          public Builder mergeFrom(
+              com.google.gwt.dev.protobuf.CodedInputStream input,
+              com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+              throws java.io.IOException {
+            com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+              com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+                this.getUnknownFields());
+            while (true) {
+              int tag = input.readTag();
+              switch (tag) {
+                case 0:
+                  this.setUnknownFields(unknownFields.build());
+                  return this;
+                default: {
+                  if (!parseUnknownField(input, unknownFields,
+                                         extensionRegistry, tag)) {
+                    this.setUnknownFields(unknownFields.build());
+                    return this;
+                  }
+                  break;
+                }
+                case 8: {
+                  int rawValue = input.readEnum();
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType.valueOf(rawValue);
+                  if (value == null) {
+                    unknownFields.mergeVarintField(1, rawValue);
+                  } else {
+                    setResponseType(value);
+                  }
+                  break;
+                }
+                case 18: {
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.newBuilder();
+                  if (hasCapabilityExchange()) {
+                    subBuilder.mergeFrom(getCapabilityExchange());
+                  }
+                  input.readMessage(subBuilder, extensionRegistry);
+                  setCapabilityExchange(subBuilder.buildPartial());
+                  break;
+                }
+                case 26: {
+                  com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.newBuilder();
+                  if (hasRestartWebServer()) {
+                    subBuilder.mergeFrom(getRestartWebServer());
+                  }
+                  input.readMessage(subBuilder, extensionRegistry);
+                  setRestartWebServer(subBuilder.buildPartial());
+                  break;
+                }
+              }
+            }
+          }
+          
+          
+          // required .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.ResponseType responseType = 1;
+          public boolean hasResponseType() {
+            return result.hasResponseType();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType getResponseType() {
+            return result.getResponseType();
+          }
+          public Builder setResponseType(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasResponseType = true;
+            result.responseType_ = value;
+            return this;
+          }
+          public Builder clearResponseType() {
+            result.hasResponseType = false;
+            result.responseType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.ResponseType.CAPABILITY_EXCHANGE;
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.CapabilityExchange capabilityExchange = 2;
+          public boolean hasCapabilityExchange() {
+            return result.hasCapabilityExchange();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange getCapabilityExchange() {
+            return result.getCapabilityExchange();
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = value;
+            return this;
+          }
+          public Builder setCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Builder builderForValue) {
+            result.hasCapabilityExchange = true;
+            result.capabilityExchange_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeCapabilityExchange(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange value) {
+            if (result.hasCapabilityExchange() &&
+                result.capabilityExchange_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance()) {
+              result.capabilityExchange_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.newBuilder(result.capabilityExchange_).mergeFrom(value).buildPartial();
+            } else {
+              result.capabilityExchange_ = value;
+            }
+            result.hasCapabilityExchange = true;
+            return this;
+          }
+          public Builder clearCapabilityExchange() {
+            result.hasCapabilityExchange = false;
+            result.capabilityExchange_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.getDefaultInstance();
+            return this;
+          }
+          
+          // optional .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse.RestartWebServer restartWebServer = 3;
+          public boolean hasRestartWebServer() {
+            return result.hasRestartWebServer();
+          }
+          public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer getRestartWebServer() {
+            return result.getRestartWebServer();
+          }
+          public Builder setRestartWebServer(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer value) {
+            if (value == null) {
+              throw new NullPointerException();
+            }
+            result.hasRestartWebServer = true;
+            result.restartWebServer_ = value;
+            return this;
+          }
+          public Builder setRestartWebServer(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.Builder builderForValue) {
+            result.hasRestartWebServer = true;
+            result.restartWebServer_ = builderForValue.build();
+            return this;
+          }
+          public Builder mergeRestartWebServer(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer value) {
+            if (result.hasRestartWebServer() &&
+                result.restartWebServer_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance()) {
+              result.restartWebServer_ =
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.newBuilder(result.restartWebServer_).mergeFrom(value).buildPartial();
+            } else {
+              result.restartWebServer_ = value;
+            }
+            result.hasRestartWebServer = true;
+            return this;
+          }
+          public Builder clearRestartWebServer() {
+            result.hasRestartWebServer = false;
+            result.restartWebServer_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.getDefaultInstance();
+            return this;
+          }
+        }
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+        }
+        
+        static {
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
         }
       }
-
-      private static final Response defaultInstance = new Response();
-
+      
       // required uint32 requestId = 1;
       public static final int REQUESTID_FIELD_NUMBER = 1;
-
-      // optional
-      // .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse
-      // viewerResponse = 2;
-      public static final int VIEWERRESPONSE_FIELD_NUMBER = 2;
-
-      static {
-        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-      }
-
-      static {
-        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-      }
-
-      public static Response getDefaultInstance() {
-        return defaultInstance;
-      }
-
-      public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor;
-      }
-
-      public static Builder newBuilder() {
-        return Builder.create();
-      }
-
-      public static Builder newBuilder(
-          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response prototype) {
-        return newBuilder().mergeFrom(prototype);
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseDelimitedFrom(
-          java.io.InputStream input) throws java.io.IOException {
-        return newBuilder().mergeDelimitedFrom(input).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseDelimitedFrom(
-          java.io.InputStream input,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws java.io.IOException {
-        return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          byte[] data)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          byte[] data,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          com.google.gwt.dev.protobuf.ByteString data)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          com.google.gwt.dev.protobuf.ByteString data,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-        return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          com.google.gwt.dev.protobuf.CodedInputStream input)
-          throws java.io.IOException {
-        return newBuilder().mergeFrom(input).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          com.google.gwt.dev.protobuf.CodedInputStream input,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws java.io.IOException {
-        return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          java.io.InputStream input) throws java.io.IOException {
-        return newBuilder().mergeFrom(input).buildParsed();
-      }
-
-      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
-          java.io.InputStream input,
-          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-          throws java.io.IOException {
-        return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-      }
-
       private boolean hasRequestId;
-
       private int requestId_ = 0;
-
+      public boolean hasRequestId() { return hasRequestId; }
+      public int getRequestId() { return requestId_; }
+      
+      // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse viewerResponse = 2;
+      public static final int VIEWERRESPONSE_FIELD_NUMBER = 2;
       private boolean hasViewerResponse;
-
       private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse viewerResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance();
-      // optional
-      // .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse
-      // devModeResponse = 3;
+      public boolean hasViewerResponse() { return hasViewerResponse; }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse getViewerResponse() { return viewerResponse_; }
+      
+      // optional .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse devModeResponse = 3;
       public static final int DEVMODERESPONSE_FIELD_NUMBER = 3;
-
       private boolean hasDevModeResponse;
       private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse devModeResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance();
-      private int memoizedSerializedSize = -1;
-
-      // Use Response.newBuilder() to construct.
-      private Response() {
-      }
-
-      public Response getDefaultInstanceForType() {
-        return defaultInstance;
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse getDevModeResponse() {
-        return devModeResponse_;
-      }
-
-      public int getRequestId() {
-        return requestId_;
-      }
-
-      public int getSerializedSize() {
-        int size = memoizedSerializedSize;
-        if (size != -1)
-          return size;
-
-        size = 0;
-        if (hasRequestId()) {
-          size += com.google.gwt.dev.protobuf.CodedOutputStream.computeUInt32Size(
-              1, getRequestId());
-        }
-        if (hasViewerResponse()) {
-          size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-              2, getViewerResponse());
-        }
-        if (hasDevModeResponse()) {
-          size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-              3, getDevModeResponse());
-        }
-        size += getUnknownFields().getSerializedSize();
-        memoizedSerializedSize = size;
-        return size;
-      }
-
-      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse getViewerResponse() {
-        return viewerResponse_;
-      }
-
-      public boolean hasDevModeResponse() {
-        return hasDevModeResponse;
-      }
-
-      public boolean hasRequestId() {
-        return hasRequestId;
-      }
-
-      public boolean hasViewerResponse() {
-        return hasViewerResponse;
-      }
-
+      public boolean hasDevModeResponse() { return hasDevModeResponse; }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse getDevModeResponse() { return devModeResponse_; }
+      
       public final boolean isInitialized() {
-        if (!hasRequestId)
-          return false;
+        if (!hasRequestId) return false;
         if (hasViewerResponse()) {
-          if (!getViewerResponse().isInitialized())
-            return false;
+          if (!getViewerResponse().isInitialized()) return false;
         }
         if (hasDevModeResponse()) {
-          if (!getDevModeResponse().isInitialized())
-            return false;
+          if (!getDevModeResponse().isInitialized()) return false;
         }
         return true;
       }
-
-      public Builder newBuilderForType() {
-        return newBuilder();
-      }
-
-      public Builder toBuilder() {
-        return newBuilder(this);
-      }
-
+      
       public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
-          throws java.io.IOException {
+                          throws java.io.IOException {
         if (hasRequestId()) {
           output.writeUInt32(1, getRequestId());
         }
@@ -10647,202 +9233,371 @@
         }
         getUnknownFields().writeTo(output);
       }
-
-      protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_fieldAccessorTable;
+      
+      private int memoizedSerializedSize = -1;
+      public int getSerializedSize() {
+        int size = memoizedSerializedSize;
+        if (size != -1) return size;
+      
+        size = 0;
+        if (hasRequestId()) {
+          size += com.google.gwt.dev.protobuf.CodedOutputStream
+            .computeUInt32Size(1, getRequestId());
+        }
+        if (hasViewerResponse()) {
+          size += com.google.gwt.dev.protobuf.CodedOutputStream
+            .computeMessageSize(2, getViewerResponse());
+        }
+        if (hasDevModeResponse()) {
+          size += com.google.gwt.dev.protobuf.CodedOutputStream
+            .computeMessageSize(3, getDevModeResponse());
+        }
+        size += getUnknownFields().getSerializedSize();
+        memoizedSerializedSize = size;
+        return size;
+      }
+      
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
+          com.google.gwt.dev.protobuf.ByteString data)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
+          com.google.gwt.dev.protobuf.ByteString data,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(byte[] data)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
+          byte[] data,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        return newBuilder().mergeFrom(data, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(java.io.InputStream input)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
+          java.io.InputStream input,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseDelimitedFrom(java.io.InputStream input)
+          throws java.io.IOException {
+        return newBuilder().mergeDelimitedFrom(input).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseDelimitedFrom(
+          java.io.InputStream input,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws java.io.IOException {
+        return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+                 .buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
+          com.google.gwt.dev.protobuf.CodedInputStream input)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input).buildParsed();
+      }
+      public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response parseFrom(
+          com.google.gwt.dev.protobuf.CodedInputStream input,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws java.io.IOException {
+        return newBuilder().mergeFrom(input, extensionRegistry)
+                 .buildParsed();
+      }
+      
+      public static Builder newBuilder() { return Builder.create(); }
+      public Builder newBuilderForType() { return newBuilder(); }
+      public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response prototype) {
+        return newBuilder().mergeFrom(prototype);
+      }
+      public Builder toBuilder() { return newBuilder(this); }
+      
+      public static final class Builder extends
+          com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response result;
+        
+        // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.newBuilder()
+        private Builder() {}
+        
+        private static Builder create() {
+          Builder builder = new Builder();
+          builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response();
+          return builder;
+        }
+        
+        protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response internalGetResult() {
+          return result;
+        }
+        
+        public Builder clear() {
+          if (result == null) {
+            throw new IllegalStateException(
+              "Cannot call clear() after build().");
+          }
+          result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response();
+          return this;
+        }
+        
+        public Builder clone() {
+          return create().mergeFrom(result);
+        }
+        
+        public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+            getDescriptorForType() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDescriptor();
+        }
+        
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response getDefaultInstanceForType() {
+          return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance();
+        }
+        
+        public boolean isInitialized() {
+          return result.isInitialized();
+        }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response build() {
+          if (result != null && !isInitialized()) {
+            throw newUninitializedMessageException(result);
+          }
+          return buildPartial();
+        }
+        
+        private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response buildParsed()
+            throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+          if (!isInitialized()) {
+            throw newUninitializedMessageException(
+              result).asInvalidProtocolBufferException();
+          }
+          return buildPartial();
+        }
+        
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response buildPartial() {
+          if (result == null) {
+            throw new IllegalStateException(
+              "build() has already been called on this Builder.");
+          }
+          com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response returnMe = result;
+          result = null;
+          return returnMe;
+        }
+        
+        public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+          if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response) {
+            return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response)other);
+          } else {
+            super.mergeFrom(other);
+            return this;
+          }
+        }
+        
+        public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response other) {
+          if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance()) return this;
+          if (other.hasRequestId()) {
+            setRequestId(other.getRequestId());
+          }
+          if (other.hasViewerResponse()) {
+            mergeViewerResponse(other.getViewerResponse());
+          }
+          if (other.hasDevModeResponse()) {
+            mergeDevModeResponse(other.getDevModeResponse());
+          }
+          this.mergeUnknownFields(other.getUnknownFields());
+          return this;
+        }
+        
+        public Builder mergeFrom(
+            com.google.gwt.dev.protobuf.CodedInputStream input,
+            com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+            throws java.io.IOException {
+          com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+            com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+              this.getUnknownFields());
+          while (true) {
+            int tag = input.readTag();
+            switch (tag) {
+              case 0:
+                this.setUnknownFields(unknownFields.build());
+                return this;
+              default: {
+                if (!parseUnknownField(input, unknownFields,
+                                       extensionRegistry, tag)) {
+                  this.setUnknownFields(unknownFields.build());
+                  return this;
+                }
+                break;
+              }
+              case 8: {
+                setRequestId(input.readUInt32());
+                break;
+              }
+              case 18: {
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.newBuilder();
+                if (hasViewerResponse()) {
+                  subBuilder.mergeFrom(getViewerResponse());
+                }
+                input.readMessage(subBuilder, extensionRegistry);
+                setViewerResponse(subBuilder.buildPartial());
+                break;
+              }
+              case 26: {
+                com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.newBuilder();
+                if (hasDevModeResponse()) {
+                  subBuilder.mergeFrom(getDevModeResponse());
+                }
+                input.readMessage(subBuilder, extensionRegistry);
+                setDevModeResponse(subBuilder.buildPartial());
+                break;
+              }
+            }
+          }
+        }
+        
+        
+        // required uint32 requestId = 1;
+        public boolean hasRequestId() {
+          return result.hasRequestId();
+        }
+        public int getRequestId() {
+          return result.getRequestId();
+        }
+        public Builder setRequestId(int value) {
+          result.hasRequestId = true;
+          result.requestId_ = value;
+          return this;
+        }
+        public Builder clearRequestId() {
+          result.hasRequestId = false;
+          result.requestId_ = 0;
+          return this;
+        }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Response.ViewerResponse viewerResponse = 2;
+        public boolean hasViewerResponse() {
+          return result.hasViewerResponse();
+        }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse getViewerResponse() {
+          return result.getViewerResponse();
+        }
+        public Builder setViewerResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse value) {
+          if (value == null) {
+            throw new NullPointerException();
+          }
+          result.hasViewerResponse = true;
+          result.viewerResponse_ = value;
+          return this;
+        }
+        public Builder setViewerResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.Builder builderForValue) {
+          result.hasViewerResponse = true;
+          result.viewerResponse_ = builderForValue.build();
+          return this;
+        }
+        public Builder mergeViewerResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse value) {
+          if (result.hasViewerResponse() &&
+              result.viewerResponse_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance()) {
+            result.viewerResponse_ =
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.newBuilder(result.viewerResponse_).mergeFrom(value).buildPartial();
+          } else {
+            result.viewerResponse_ = value;
+          }
+          result.hasViewerResponse = true;
+          return this;
+        }
+        public Builder clearViewerResponse() {
+          result.hasViewerResponse = false;
+          result.viewerResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.getDefaultInstance();
+          return this;
+        }
+        
+        // optional .com.google.gwt.dev.shell.remoteui.Message.Response.DevModeResponse devModeResponse = 3;
+        public boolean hasDevModeResponse() {
+          return result.hasDevModeResponse();
+        }
+        public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse getDevModeResponse() {
+          return result.getDevModeResponse();
+        }
+        public Builder setDevModeResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse value) {
+          if (value == null) {
+            throw new NullPointerException();
+          }
+          result.hasDevModeResponse = true;
+          result.devModeResponse_ = value;
+          return this;
+        }
+        public Builder setDevModeResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.Builder builderForValue) {
+          result.hasDevModeResponse = true;
+          result.devModeResponse_ = builderForValue.build();
+          return this;
+        }
+        public Builder mergeDevModeResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse value) {
+          if (result.hasDevModeResponse() &&
+              result.devModeResponse_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance()) {
+            result.devModeResponse_ =
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.newBuilder(result.devModeResponse_).mergeFrom(value).buildPartial();
+          } else {
+            result.devModeResponse_ = value;
+          }
+          result.hasDevModeResponse = true;
+          return this;
+        }
+        public Builder clearDevModeResponse() {
+          result.hasDevModeResponse = false;
+          result.devModeResponse_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.getDefaultInstance();
+          return this;
+        }
+      }
+      
+      static {
+        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+      }
+      
+      static {
+        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
       }
     }
-
-    private static final Message defaultInstance = new Message();
-
-    // required .com.google.gwt.dev.shell.remoteui.Message.MessageType
-    // messageType = 1;
+    
+    // required .com.google.gwt.dev.shell.remoteui.Message.MessageType messageType = 1;
     public static final int MESSAGETYPE_FIELD_NUMBER = 1;
-
-    static {
-      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
-    }
-
-    static {
-      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
-    }
-
-    public static Message getDefaultInstance() {
-      return defaultInstance;
-    }
-
-    public static final com.google.gwt.dev.protobuf.Descriptors.Descriptor getDescriptor() {
-      return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor;
-    }
-
-    public static Builder newBuilder() {
-      return Builder.create();
-    }
-
-    public static Builder newBuilder(
-        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message prototype) {
-      return newBuilder().mergeFrom(prototype);
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseDelimitedFrom(
-        java.io.InputStream input) throws java.io.IOException {
-      return newBuilder().mergeDelimitedFrom(input).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseDelimitedFrom(
-        java.io.InputStream input,
-        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-        throws java.io.IOException {
-      return newBuilder().mergeDelimitedFrom(input, extensionRegistry).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        byte[] data)
-        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-      return newBuilder().mergeFrom(data).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        byte[] data,
-        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-      return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        com.google.gwt.dev.protobuf.ByteString data)
-        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-      return newBuilder().mergeFrom(data).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        com.google.gwt.dev.protobuf.ByteString data,
-        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
-      return newBuilder().mergeFrom(data, extensionRegistry).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        com.google.gwt.dev.protobuf.CodedInputStream input)
-        throws java.io.IOException {
-      return newBuilder().mergeFrom(input).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        com.google.gwt.dev.protobuf.CodedInputStream input,
-        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-        throws java.io.IOException {
-      return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        java.io.InputStream input) throws java.io.IOException {
-      return newBuilder().mergeFrom(input).buildParsed();
-    }
-
-    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
-        java.io.InputStream input,
-        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
-        throws java.io.IOException {
-      return newBuilder().mergeFrom(input, extensionRegistry).buildParsed();
-    }
-
     private boolean hasMessageType;
     private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType messageType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType.REQUEST;
-
+    public boolean hasMessageType() { return hasMessageType; }
+    public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType getMessageType() { return messageType_; }
+    
     // optional .com.google.gwt.dev.shell.remoteui.Message.Request request = 2;
     public static final int REQUEST_FIELD_NUMBER = 2;
-
     private boolean hasRequest;
-
     private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request request_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance();
-    // optional .com.google.gwt.dev.shell.remoteui.Message.Response response =
-    // 3;
+    public boolean hasRequest() { return hasRequest; }
+    public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request getRequest() { return request_; }
+    
+    // optional .com.google.gwt.dev.shell.remoteui.Message.Response response = 3;
     public static final int RESPONSE_FIELD_NUMBER = 3;
-
     private boolean hasResponse;
     private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response response_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance();
-    private int memoizedSerializedSize = -1;
-
-    // Use Message.newBuilder() to construct.
-    private Message() {
-    }
-
-    public Message getDefaultInstanceForType() {
-      return defaultInstance;
-    }
-
-    public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType getMessageType() {
-      return messageType_;
-    }
-
-    public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request getRequest() {
-      return request_;
-    }
-
-    public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response getResponse() {
-      return response_;
-    }
-
-    public int getSerializedSize() {
-      int size = memoizedSerializedSize;
-      if (size != -1)
-        return size;
-
-      size = 0;
-      if (hasMessageType()) {
-        size += com.google.gwt.dev.protobuf.CodedOutputStream.computeEnumSize(
-            1, getMessageType().getNumber());
-      }
-      if (hasRequest()) {
-        size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-            2, getRequest());
-      }
-      if (hasResponse()) {
-        size += com.google.gwt.dev.protobuf.CodedOutputStream.computeMessageSize(
-            3, getResponse());
-      }
-      size += getUnknownFields().getSerializedSize();
-      memoizedSerializedSize = size;
-      return size;
-    }
-
-    public boolean hasMessageType() {
-      return hasMessageType;
-    }
-
-    public boolean hasRequest() {
-      return hasRequest;
-    }
-
-    public boolean hasResponse() {
-      return hasResponse;
-    }
-
+    public boolean hasResponse() { return hasResponse; }
+    public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response getResponse() { return response_; }
+    
     public final boolean isInitialized() {
-      if (!hasMessageType)
-        return false;
+      if (!hasMessageType) return false;
       if (hasRequest()) {
-        if (!getRequest().isInitialized())
-          return false;
+        if (!getRequest().isInitialized()) return false;
       }
       if (hasResponse()) {
-        if (!getResponse().isInitialized())
-          return false;
+        if (!getResponse().isInitialized()) return false;
       }
       return true;
     }
-
-    public Builder newBuilderForType() {
-      return newBuilder();
-    }
-
-    public Builder toBuilder() {
-      return newBuilder(this);
-    }
-
+    
     public void writeTo(com.google.gwt.dev.protobuf.CodedOutputStream output)
-        throws java.io.IOException {
+                        throws java.io.IOException {
       if (hasMessageType()) {
         output.writeEnum(1, getMessageType().getNumber());
       }
@@ -10854,406 +9609,847 @@
       }
       getUnknownFields().writeTo(output);
     }
-
-    protected com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internalGetFieldAccessorTable() {
-      return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internal_static_com_google_gwt_dev_shell_remoteui_Message_fieldAccessorTable;
+    
+    private int memoizedSerializedSize = -1;
+    public int getSerializedSize() {
+      int size = memoizedSerializedSize;
+      if (size != -1) return size;
+    
+      size = 0;
+      if (hasMessageType()) {
+        size += com.google.gwt.dev.protobuf.CodedOutputStream
+          .computeEnumSize(1, getMessageType().getNumber());
+      }
+      if (hasRequest()) {
+        size += com.google.gwt.dev.protobuf.CodedOutputStream
+          .computeMessageSize(2, getRequest());
+      }
+      if (hasResponse()) {
+        size += com.google.gwt.dev.protobuf.CodedOutputStream
+          .computeMessageSize(3, getResponse());
+      }
+      size += getUnknownFields().getSerializedSize();
+      memoizedSerializedSize = size;
+      return size;
+    }
+    
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
+        com.google.gwt.dev.protobuf.ByteString data)
+        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+      return newBuilder().mergeFrom(data).buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
+        com.google.gwt.dev.protobuf.ByteString data,
+        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+      return newBuilder().mergeFrom(data, extensionRegistry)
+               .buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(byte[] data)
+        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+      return newBuilder().mergeFrom(data).buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
+        byte[] data,
+        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+        throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+      return newBuilder().mergeFrom(data, extensionRegistry)
+               .buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(java.io.InputStream input)
+        throws java.io.IOException {
+      return newBuilder().mergeFrom(input).buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
+        java.io.InputStream input,
+        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+        throws java.io.IOException {
+      return newBuilder().mergeFrom(input, extensionRegistry)
+               .buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseDelimitedFrom(java.io.InputStream input)
+        throws java.io.IOException {
+      return newBuilder().mergeDelimitedFrom(input).buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseDelimitedFrom(
+        java.io.InputStream input,
+        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+        throws java.io.IOException {
+      return newBuilder().mergeDelimitedFrom(input, extensionRegistry)
+               .buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
+        com.google.gwt.dev.protobuf.CodedInputStream input)
+        throws java.io.IOException {
+      return newBuilder().mergeFrom(input).buildParsed();
+    }
+    public static com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message parseFrom(
+        com.google.gwt.dev.protobuf.CodedInputStream input,
+        com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+        throws java.io.IOException {
+      return newBuilder().mergeFrom(input, extensionRegistry)
+               .buildParsed();
+    }
+    
+    public static Builder newBuilder() { return Builder.create(); }
+    public Builder newBuilderForType() { return newBuilder(); }
+    public static Builder newBuilder(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message prototype) {
+      return newBuilder().mergeFrom(prototype);
+    }
+    public Builder toBuilder() { return newBuilder(this); }
+    
+    public static final class Builder extends
+        com.google.gwt.dev.protobuf.GeneratedMessage.Builder<Builder> {
+      private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message result;
+      
+      // Construct using com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.newBuilder()
+      private Builder() {}
+      
+      private static Builder create() {
+        Builder builder = new Builder();
+        builder.result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message();
+        return builder;
+      }
+      
+      protected com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message internalGetResult() {
+        return result;
+      }
+      
+      public Builder clear() {
+        if (result == null) {
+          throw new IllegalStateException(
+            "Cannot call clear() after build().");
+        }
+        result = new com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message();
+        return this;
+      }
+      
+      public Builder clone() {
+        return create().mergeFrom(result);
+      }
+      
+      public com.google.gwt.dev.protobuf.Descriptors.Descriptor
+          getDescriptorForType() {
+        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDescriptor();
+      }
+      
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message getDefaultInstanceForType() {
+        return com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDefaultInstance();
+      }
+      
+      public boolean isInitialized() {
+        return result.isInitialized();
+      }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message build() {
+        if (result != null && !isInitialized()) {
+          throw newUninitializedMessageException(result);
+        }
+        return buildPartial();
+      }
+      
+      private com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message buildParsed()
+          throws com.google.gwt.dev.protobuf.InvalidProtocolBufferException {
+        if (!isInitialized()) {
+          throw newUninitializedMessageException(
+            result).asInvalidProtocolBufferException();
+        }
+        return buildPartial();
+      }
+      
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message buildPartial() {
+        if (result == null) {
+          throw new IllegalStateException(
+            "build() has already been called on this Builder.");
+        }
+        com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message returnMe = result;
+        result = null;
+        return returnMe;
+      }
+      
+      public Builder mergeFrom(com.google.gwt.dev.protobuf.Message other) {
+        if (other instanceof com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message) {
+          return mergeFrom((com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message)other);
+        } else {
+          super.mergeFrom(other);
+          return this;
+        }
+      }
+      
+      public Builder mergeFrom(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message other) {
+        if (other == com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.getDefaultInstance()) return this;
+        if (other.hasMessageType()) {
+          setMessageType(other.getMessageType());
+        }
+        if (other.hasRequest()) {
+          mergeRequest(other.getRequest());
+        }
+        if (other.hasResponse()) {
+          mergeResponse(other.getResponse());
+        }
+        this.mergeUnknownFields(other.getUnknownFields());
+        return this;
+      }
+      
+      public Builder mergeFrom(
+          com.google.gwt.dev.protobuf.CodedInputStream input,
+          com.google.gwt.dev.protobuf.ExtensionRegistryLite extensionRegistry)
+          throws java.io.IOException {
+        com.google.gwt.dev.protobuf.UnknownFieldSet.Builder unknownFields =
+          com.google.gwt.dev.protobuf.UnknownFieldSet.newBuilder(
+            this.getUnknownFields());
+        while (true) {
+          int tag = input.readTag();
+          switch (tag) {
+            case 0:
+              this.setUnknownFields(unknownFields.build());
+              return this;
+            default: {
+              if (!parseUnknownField(input, unknownFields,
+                                     extensionRegistry, tag)) {
+                this.setUnknownFields(unknownFields.build());
+                return this;
+              }
+              break;
+            }
+            case 8: {
+              int rawValue = input.readEnum();
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType value = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType.valueOf(rawValue);
+              if (value == null) {
+                unknownFields.mergeVarintField(1, rawValue);
+              } else {
+                setMessageType(value);
+              }
+              break;
+            }
+            case 18: {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.newBuilder();
+              if (hasRequest()) {
+                subBuilder.mergeFrom(getRequest());
+              }
+              input.readMessage(subBuilder, extensionRegistry);
+              setRequest(subBuilder.buildPartial());
+              break;
+            }
+            case 26: {
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.Builder subBuilder = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.newBuilder();
+              if (hasResponse()) {
+                subBuilder.mergeFrom(getResponse());
+              }
+              input.readMessage(subBuilder, extensionRegistry);
+              setResponse(subBuilder.buildPartial());
+              break;
+            }
+          }
+        }
+      }
+      
+      
+      // required .com.google.gwt.dev.shell.remoteui.Message.MessageType messageType = 1;
+      public boolean hasMessageType() {
+        return result.hasMessageType();
+      }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType getMessageType() {
+        return result.getMessageType();
+      }
+      public Builder setMessageType(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType value) {
+        if (value == null) {
+          throw new NullPointerException();
+        }
+        result.hasMessageType = true;
+        result.messageType_ = value;
+        return this;
+      }
+      public Builder clearMessageType() {
+        result.hasMessageType = false;
+        result.messageType_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.MessageType.REQUEST;
+        return this;
+      }
+      
+      // optional .com.google.gwt.dev.shell.remoteui.Message.Request request = 2;
+      public boolean hasRequest() {
+        return result.hasRequest();
+      }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request getRequest() {
+        return result.getRequest();
+      }
+      public Builder setRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request value) {
+        if (value == null) {
+          throw new NullPointerException();
+        }
+        result.hasRequest = true;
+        result.request_ = value;
+        return this;
+      }
+      public Builder setRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.Builder builderForValue) {
+        result.hasRequest = true;
+        result.request_ = builderForValue.build();
+        return this;
+      }
+      public Builder mergeRequest(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request value) {
+        if (result.hasRequest() &&
+            result.request_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance()) {
+          result.request_ =
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.newBuilder(result.request_).mergeFrom(value).buildPartial();
+        } else {
+          result.request_ = value;
+        }
+        result.hasRequest = true;
+        return this;
+      }
+      public Builder clearRequest() {
+        result.hasRequest = false;
+        result.request_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.getDefaultInstance();
+        return this;
+      }
+      
+      // optional .com.google.gwt.dev.shell.remoteui.Message.Response response = 3;
+      public boolean hasResponse() {
+        return result.hasResponse();
+      }
+      public com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response getResponse() {
+        return result.getResponse();
+      }
+      public Builder setResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response value) {
+        if (value == null) {
+          throw new NullPointerException();
+        }
+        result.hasResponse = true;
+        result.response_ = value;
+        return this;
+      }
+      public Builder setResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.Builder builderForValue) {
+        result.hasResponse = true;
+        result.response_ = builderForValue.build();
+        return this;
+      }
+      public Builder mergeResponse(com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response value) {
+        if (result.hasResponse() &&
+            result.response_ != com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance()) {
+          result.response_ =
+            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.newBuilder(result.response_).mergeFrom(value).buildPartial();
+        } else {
+          result.response_ = value;
+        }
+        result.hasResponse = true;
+        return this;
+      }
+      public Builder clearResponse() {
+        result.hasResponse = false;
+        result.response_ = com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.getDefaultInstance();
+        return this;
+      }
+    }
+    
+    static {
+      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.getDescriptor();
+    }
+    
+    static {
+      com.google.gwt.dev.shell.remoteui.RemoteMessageProto.internalForceInit();
     }
   }
-
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_fieldAccessorTable;
-
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor;
-  private static com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_fieldAccessorTable;
-  private static com.google.gwt.dev.protobuf.Descriptors.FileDescriptor descriptor;
-  static {
-    java.lang.String[] descriptorData = {
-        "\n5com/google/gwt/dev/shell/remoteui/remo"
-            + "temessage.proto\022!com.google.gwt.dev.shel"
-            + "l.remoteui\"\363$\n\007Message\022K\n\013messageType\030\001 "
-            + "\002(\01626.com.google.gwt.dev.shell.remoteui."
-            + "Message.MessageType\022C\n\007request\030\002 \001(\01322.c"
-            + "om.google.gwt.dev.shell.remoteui.Message"
-            + ".Request\022E\n\010response\030\003 \001(\01323.com.google."
-            + "gwt.dev.shell.remoteui.Message.Response\032"
-            + "\234\025\n\007Request\022S\n\013serviceType\030\001 \002(\0162>.com.g"
-            + "oogle.gwt.dev.shell.remoteui.Message.Req",
-        "uest.ServiceType\022\021\n\trequestId\030\002 \001(\r\022W\n\rv"
-            + "iewerRequest\030\003 \001(\0132@.com.google.gwt.dev."
-            + "shell.remoteui.Message.Request.ViewerReq"
-            + "uest\022Y\n\016devModeRequest\030\004 \001(\0132A.com.googl"
-            + "e.gwt.dev.shell.remoteui.Message.Request"
-            + ".DevModeRequest\032\212\017\n\rViewerRequest\022a\n\013req"
-            + "uestType\030\001 \002(\0162L.com.google.gwt.dev.shel"
-            + "l.remoteui.Message.Request.ViewerRequest"
-            + ".RequestType\022o\n\022capabilityExchange\030\002 \001(\013"
-            + "2S.com.google.gwt.dev.shell.remoteui.Mes",
-        "sage.Request.ViewerRequest.CapabilityExc"
-            + "hange\022W\n\006addLog\030\003 \001(\0132G.com.google.gwt.d"
-            + "ev.shell.remoteui.Message.Request.Viewer"
-            + "Request.AddLog\022c\n\014addLogBranch\030\004 \001(\0132M.c"
-            + "om.google.gwt.dev.shell.remoteui.Message"
-            + ".Request.ViewerRequest.AddLogBranch\022a\n\013a"
-            + "ddLogEntry\030\005 \001(\0132L.com.google.gwt.dev.sh"
-            + "ell.remoteui.Message.Request.ViewerReque"
-            + "st.AddLogEntry\022e\n\rdisconnectLog\030\006 \001(\0132N."
-            + "com.google.gwt.dev.shell.remoteui.Messag",
-        "e.Request.ViewerRequest.DisconnectLog\032\024\n"
-            + "\022CapabilityExchange\032\373\004\n\006AddLog\022]\n\004type\030\001"
-            + " \002(\0162O.com.google.gwt.dev.shell.remoteui"
-            + ".Message.Request.ViewerRequest.AddLog.Lo"
-            + "gType\022d\n\tmoduleLog\030\002 \001(\0132Q.com.google.gw"
-            + "t.dev.shell.remoteui.Message.Request.Vie"
-            + "werRequest.AddLog.ModuleLog\022d\n\tserverLog"
-            + "\030\003 \001(\0132Q.com.google.gwt.dev.shell.remote"
-            + "ui.Message.Request.ViewerRequest.AddLog."
-            + "ServerLog\022`\n\007mainLog\030\004 \001(\0132O.com.google.",
-        "gwt.dev.shell.remoteui.Message.Request.V"
-            + "iewerRequest.AddLog.MainLog\032\177\n\tModuleLog"
-            + "\022\014\n\004name\030\001 \002(\t\022\014\n\004icon\030\002 \001(\014\022\022\n\nsessionK"
-            + "ey\030\003 \001(\t\022\021\n\tuserAgent\030\004 \001(\t\022\013\n\003url\030\005 \001(\t"
-            + "\022\016\n\006tabKey\030\006 \001(\t\022\022\n\nremoteHost\030\007 \001(\t\032\'\n\t"
-            + "ServerLog\022\014\n\004name\030\001 \002(\t\022\014\n\004icon\030\002 \001(\014\032\t\n"
-            + "\007MainLog\"/\n\007LogType\022\010\n\004MAIN\020\000\022\n\n\006MODULE\020"
-            + "\001\022\016\n\nWEB_SERVER\020\002\032\306\001\n\007LogData\022\017\n\007summary"
-            + "\030\001 \002(\t\022\r\n\005level\030\002 \001(\t\022\017\n\007details\030\003 \001(\t\022c"
-            + "\n\010helpInfo\030\004 \001(\0132Q.com.google.gwt.dev.sh",
-        "ell.remoteui.Message.Request.ViewerReque"
-            + "st.LogData.HelpInfo\032%\n\010HelpInfo\022\013\n\003url\030\001"
-            + " \001(\t\022\014\n\004text\030\002 \001(\t\032\231\001\n\014AddLogBranch\022\027\n\017p"
-            + "arentLogHandle\030\001 \002(\r\022\025\n\rindexInParent\030\002 "
-            + "\002(\r\022Y\n\007logData\030\003 \002(\0132H.com.google.gwt.de"
-            + "v.shell.remoteui.Message.Request.ViewerR"
-            + "equest.LogData\032\217\001\n\013AddLogEntry\022\021\n\tlogHan"
-            + "dle\030\001 \002(\r\022\022\n\nindexInLog\030\002 \002(\r\022Y\n\007logData"
-            + "\030\003 \002(\0132H.com.google.gwt.dev.shell.remote"
-            + "ui.Message.Request.ViewerRequest.LogData",
-        "\032\"\n\rDisconnectLog\022\021\n\tlogHandle\030\001 \002(\r\"n\n\013"
-            + "RequestType\022\027\n\023CAPABILITY_EXCHANGE\020\000\022\013\n\007"
-            + "ADD_LOG\020\001\022\022\n\016ADD_LOG_BRANCH\020\002\022\021\n\rADD_LOG"
-            + "_ENTRY\020\003\022\022\n\016DISCONNECT_LOG\020\004\032\276\003\n\016DevMode"
-            + "Request\022b\n\013requestType\030\001 \002(\0162M.com.googl"
-            + "e.gwt.dev.shell.remoteui.Message.Request"
-            + ".DevModeRequest.RequestType\022p\n\022capabilit"
-            + "yExchange\030\002 \001(\0132T.com.google.gwt.dev.she"
-            + "ll.remoteui.Message.Request.DevModeReque"
-            + "st.CapabilityExchange\022l\n\020restartWebServe",
-        "r\030\003 \001(\0132R.com.google.gwt.dev.shell.remot"
-            + "eui.Message.Request.DevModeRequest.Resta"
-            + "rtWebServer\032\024\n\022CapabilityExchange\032\022\n\020Res"
-            + "tartWebServer\">\n\013RequestType\022\027\n\023CAPABILI"
-            + "TY_EXCHANGE\020\000\022\026\n\022RESTART_WEB_SERVER\020\001\"\'\n"
-            + "\013ServiceType\022\n\n\006VIEWER\020\000\022\014\n\010DEV_MODE\020\001\032\305"
-            + "\r\n\010Response\022\021\n\trequestId\030\001 \002(\r\022Z\n\016viewer"
-            + "Response\030\002 \001(\0132B.com.google.gwt.dev.shel"
-            + "l.remoteui.Message.Response.ViewerRespon"
-            + "se\022\\\n\017devModeResponse\030\003 \001(\0132C.com.google",
-        ".gwt.dev.shell.remoteui.Message.Response"
-            + ".DevModeResponse\032\265\006\n\016ViewerResponse\022e\n\014r"
-            + "esponseType\030\001 \002(\0162O.com.google.gwt.dev.s"
-            + "hell.remoteui.Message.Response.ViewerRes"
-            + "ponse.ResponseType\022q\n\022capabilityExchange"
-            + "\030\002 \001(\0132U.com.google.gwt.dev.shell.remote"
-            + "ui.Message.Response.ViewerResponse.Capab"
-            + "ilityExchange\022Y\n\006addLog\030\003 \001(\0132I.com.goog"
-            + "le.gwt.dev.shell.remoteui.Message.Respon"
-            + "se.ViewerResponse.AddLog\022e\n\014addLogBranch",
-        "\030\004 \001(\0132O.com.google.gwt.dev.shell.remote"
-            + "ui.Message.Response.ViewerResponse.AddLo"
-            + "gBranch\032\374\001\n\022CapabilityExchange\022v\n\014capabi"
-            + "lities\030\002 \003(\0132`.com.google.gwt.dev.shell."
-            + "remoteui.Message.Response.ViewerResponse"
-            + ".CapabilityExchange.Capability\032n\n\nCapabi"
-            + "lity\022`\n\ncapability\030\001 \002(\0162L.com.google.gw"
-            + "t.dev.shell.remoteui.Message.Request.Vie"
-            + "werRequest.RequestType\032\033\n\006AddLog\022\021\n\tlogH"
-            + "andle\030\001 \002(\r\032!\n\014AddLogBranch\022\021\n\tlogHandle",
-        "\030\001 \002(\r\"H\n\014ResponseType\022\027\n\023CAPABILITY_EXC"
-            + "HANGE\020\000\022\013\n\007ADD_LOG\020\001\022\022\n\016ADD_LOG_BRANCH\020\002"
-            + "\032\263\005\n\017DevModeResponse\022f\n\014responseType\030\001 \002"
-            + "(\0162P.com.google.gwt.dev.shell.remoteui.M"
-            + "essage.Response.DevModeResponse.Response"
-            + "Type\022r\n\022capabilityExchange\030\002 \001(\0132V.com.g"
-            + "oogle.gwt.dev.shell.remoteui.Message.Res"
-            + "ponse.DevModeResponse.CapabilityExchange"
-            + "\022n\n\020restartWebServer\030\003 \001(\0132T.com.google."
-            + "gwt.dev.shell.remoteui.Message.Response.",
-        "DevModeResponse.RestartWebServer\032\376\001\n\022Cap"
-            + "abilityExchange\022w\n\014capabilities\030\002 \003(\0132a."
-            + "com.google.gwt.dev.shell.remoteui.Messag"
-            + "e.Response.DevModeResponse.CapabilityExc"
-            + "hange.Capability\032o\n\nCapability\022a\n\ncapabi"
-            + "lity\030\001 \002(\0162M.com.google.gwt.dev.shell.re"
-            + "moteui.Message.Request.DevModeRequest.Re"
-            + "questType\032\022\n\020RestartWebServer\"?\n\014Respons"
-            + "eType\022\027\n\023CAPABILITY_EXCHANGE\020\000\022\026\n\022RESTAR"
-            + "T_WEB_SERVER\020\001\"(\n\013MessageType\022\013\n\007REQUEST",
-        "\020\000\022\014\n\010RESPONSE\020\001B\024B\022RemoteMessageProto"};
-    com.google.gwt.dev.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner = new com.google.gwt.dev.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner() {
-      public com.google.gwt.dev.protobuf.ExtensionRegistry assignDescriptors(
-          com.google.gwt.dev.protobuf.Descriptors.FileDescriptor root) {
-        descriptor = root;
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor = getDescriptor().getMessageTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor,
-            new java.lang.String[] {"MessageType", "Request", "Response",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor,
-            new java.lang.String[] {
-                "ServiceType", "RequestId", "ViewerRequest", "DevModeRequest",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor,
-            new java.lang.String[] {
-                "RequestType", "CapabilityExchange", "AddLog", "AddLogBranch",
-                "AddLogEntry", "DisconnectLog",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor,
-            new java.lang.String[] {},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor,
-            new java.lang.String[] {
-                "Type", "ModuleLog", "ServerLog", "MainLog",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor,
-            new java.lang.String[] {
-                "Name", "Icon", "SessionKey", "UserAgent", "Url", "TabKey",
-                "RemoteHost",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor,
-            new java.lang.String[] {"Name", "Icon",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor.getNestedTypes().get(
-            2);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor,
-            new java.lang.String[] {},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(
-            2);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor,
-            new java.lang.String[] {"Summary", "Level", "Details", "HelpInfo",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor,
-            new java.lang.String[] {"Url", "Text",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(
-            3);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor,
-            new java.lang.String[] {
-                "ParentLogHandle", "IndexInParent", "LogData",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(
-            4);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor,
-            new java.lang.String[] {"LogHandle", "IndexInLog", "LogData",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(
-            5);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor,
-            new java.lang.String[] {"LogHandle",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor,
-            new java.lang.String[] {
-                "RequestType", "CapabilityExchange", "RestartWebServer",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor,
-            new java.lang.String[] {},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor,
-            new java.lang.String[] {},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor,
-            new java.lang.String[] {
-                "RequestId", "ViewerResponse", "DevModeResponse",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor,
-            new java.lang.String[] {
-                "ResponseType", "CapabilityExchange", "AddLog", "AddLogBranch",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor,
-            new java.lang.String[] {"Capabilities",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor,
-            new java.lang.String[] {"Capability",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor,
-            new java.lang.String[] {"LogHandle",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor.getNestedTypes().get(
-            2);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor,
-            new java.lang.String[] {"LogHandle",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor,
-            new java.lang.String[] {
-                "ResponseType", "CapabilityExchange", "RestartWebServer",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor,
-            new java.lang.String[] {"Capabilities",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor.getNestedTypes().get(
-            0);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor,
-            new java.lang.String[] {"Capability",},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder.class);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor = internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor.getNestedTypes().get(
-            1);
-        internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_fieldAccessorTable = new com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
-            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor,
-            new java.lang.String[] {},
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.class,
-            com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.Builder.class);
-        return null;
-      }
-    };
-    com.google.gwt.dev.protobuf.Descriptors.FileDescriptor.internalBuildGeneratedFileFrom(
-        descriptorData,
-        new com.google.gwt.dev.protobuf.Descriptors.FileDescriptor[] {},
-        assigner);
-  }
-
-  public static com.google.gwt.dev.protobuf.Descriptors.FileDescriptor getDescriptor() {
+  
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_Initialize_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_Initialize_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_fieldAccessorTable;
+  private static com.google.gwt.dev.protobuf.Descriptors.Descriptor
+    internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor;
+  private static
+    com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable
+      internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_fieldAccessorTable;
+  
+  public static com.google.gwt.dev.protobuf.Descriptors.FileDescriptor
+      getDescriptor() {
     return descriptor;
   }
-
-  public static void internalForceInit() {
+  private static com.google.gwt.dev.protobuf.Descriptors.FileDescriptor
+      descriptor;
+  static {
+    java.lang.String[] descriptorData = {
+      "\n>core/src/com/google/gwt/dev/shell/remo" +
+      "teui/remotemessage.proto\022!com.google.gwt" +
+      ".dev.shell.remoteui\"\266&\n\007Message\022K\n\013messa" +
+      "geType\030\001 \002(\01626.com.google.gwt.dev.shell." +
+      "remoteui.Message.MessageType\022C\n\007request\030" +
+      "\002 \001(\01322.com.google.gwt.dev.shell.remoteu" +
+      "i.Message.Request\022E\n\010response\030\003 \001(\01323.co" +
+      "m.google.gwt.dev.shell.remoteui.Message." +
+      "Response\032\337\026\n\007Request\022S\n\013serviceType\030\001 \002(" +
+      "\0162>.com.google.gwt.dev.shell.remoteui.Me",
+      "ssage.Request.ServiceType\022\021\n\trequestId\030\002" +
+      " \001(\r\022W\n\rviewerRequest\030\003 \001(\0132@.com.google" +
+      ".gwt.dev.shell.remoteui.Message.Request." +
+      "ViewerRequest\022Y\n\016devModeRequest\030\004 \001(\0132A." +
+      "com.google.gwt.dev.shell.remoteui.Messag" +
+      "e.Request.DevModeRequest\032\315\020\n\rViewerReque" +
+      "st\022a\n\013requestType\030\001 \002(\0162L.com.google.gwt" +
+      ".dev.shell.remoteui.Message.Request.View" +
+      "erRequest.RequestType\022o\n\022capabilityExcha" +
+      "nge\030\002 \001(\0132S.com.google.gwt.dev.shell.rem",
+      "oteui.Message.Request.ViewerRequest.Capa" +
+      "bilityExchange\022W\n\006addLog\030\003 \001(\0132G.com.goo" +
+      "gle.gwt.dev.shell.remoteui.Message.Reque" +
+      "st.ViewerRequest.AddLog\022c\n\014addLogBranch\030" +
+      "\004 \001(\0132M.com.google.gwt.dev.shell.remoteu" +
+      "i.Message.Request.ViewerRequest.AddLogBr" +
+      "anch\022a\n\013addLogEntry\030\005 \001(\0132L.com.google.g" +
+      "wt.dev.shell.remoteui.Message.Request.Vi" +
+      "ewerRequest.AddLogEntry\022e\n\rdisconnectLog" +
+      "\030\006 \001(\0132N.com.google.gwt.dev.shell.remote",
+      "ui.Message.Request.ViewerRequest.Disconn" +
+      "ectLog\022_\n\ninitialize\030\007 \001(\0132K.com.google." +
+      "gwt.dev.shell.remoteui.Message.Request.V" +
+      "iewerRequest.Initialize\032\024\n\022CapabilityExc" +
+      "hange\032\373\004\n\006AddLog\022]\n\004type\030\001 \002(\0162O.com.goo" +
+      "gle.gwt.dev.shell.remoteui.Message.Reque" +
+      "st.ViewerRequest.AddLog.LogType\022d\n\tmodul" +
+      "eLog\030\002 \001(\0132Q.com.google.gwt.dev.shell.re" +
+      "moteui.Message.Request.ViewerRequest.Add" +
+      "Log.ModuleLog\022d\n\tserverLog\030\003 \001(\0132Q.com.g",
+      "oogle.gwt.dev.shell.remoteui.Message.Req" +
+      "uest.ViewerRequest.AddLog.ServerLog\022`\n\007m" +
+      "ainLog\030\004 \001(\0132O.com.google.gwt.dev.shell." +
+      "remoteui.Message.Request.ViewerRequest.A" +
+      "ddLog.MainLog\032\177\n\tModuleLog\022\014\n\004name\030\001 \002(\t" +
+      "\022\014\n\004icon\030\002 \001(\014\022\022\n\nsessionKey\030\003 \001(\t\022\021\n\tus" +
+      "erAgent\030\004 \001(\t\022\013\n\003url\030\005 \001(\t\022\016\n\006tabKey\030\006 \001" +
+      "(\t\022\022\n\nremoteHost\030\007 \001(\t\032\'\n\tServerLog\022\014\n\004n" +
+      "ame\030\001 \002(\t\022\014\n\004icon\030\002 \001(\014\032\t\n\007MainLog\"/\n\007Lo" +
+      "gType\022\010\n\004MAIN\020\000\022\n\n\006MODULE\020\001\022\016\n\nWEB_SERVE",
+      "R\020\002\032\306\001\n\007LogData\022\017\n\007summary\030\001 \002(\t\022\r\n\005leve" +
+      "l\030\002 \001(\t\022\017\n\007details\030\003 \001(\t\022c\n\010helpInfo\030\004 \001" +
+      "(\0132Q.com.google.gwt.dev.shell.remoteui.M" +
+      "essage.Request.ViewerRequest.LogData.Hel" +
+      "pInfo\032%\n\010HelpInfo\022\013\n\003url\030\001 \001(\t\022\014\n\004text\030\002" +
+      " \001(\t\032\231\001\n\014AddLogBranch\022\027\n\017parentLogHandle" +
+      "\030\001 \002(\r\022\025\n\rindexInParent\030\002 \002(\r\022Y\n\007logData" +
+      "\030\003 \002(\0132H.com.google.gwt.dev.shell.remote" +
+      "ui.Message.Request.ViewerRequest.LogData" +
+      "\032\217\001\n\013AddLogEntry\022\021\n\tlogHandle\030\001 \002(\r\022\022\n\ni",
+      "ndexInLog\030\002 \002(\r\022Y\n\007logData\030\003 \002(\0132H.com.g" +
+      "oogle.gwt.dev.shell.remoteui.Message.Req" +
+      "uest.ViewerRequest.LogData\032\"\n\rDisconnect" +
+      "Log\022\021\n\tlogHandle\030\001 \002(\r\032P\n\nInitialize\022\020\n\010" +
+      "clientId\030\001 \001(\t\022\031\n\021devModeQueryParam\030\002 \001(" +
+      "\t\022\025\n\rwebServerPort\030\003 \001(\021\"~\n\013RequestType\022" +
+      "\027\n\023CAPABILITY_EXCHANGE\020\000\022\013\n\007ADD_LOG\020\001\022\022\n" +
+      "\016ADD_LOG_BRANCH\020\002\022\021\n\rADD_LOG_ENTRY\020\003\022\022\n\016" +
+      "DISCONNECT_LOG\020\004\022\016\n\nINITIALIZE\020\005\032\276\003\n\016Dev" +
+      "ModeRequest\022b\n\013requestType\030\001 \002(\0162M.com.g",
+      "oogle.gwt.dev.shell.remoteui.Message.Req" +
+      "uest.DevModeRequest.RequestType\022p\n\022capab" +
+      "ilityExchange\030\002 \001(\0132T.com.google.gwt.dev" +
+      ".shell.remoteui.Message.Request.DevModeR" +
+      "equest.CapabilityExchange\022l\n\020restartWebS" +
+      "erver\030\003 \001(\0132R.com.google.gwt.dev.shell.r" +
+      "emoteui.Message.Request.DevModeRequest.R" +
+      "estartWebServer\032\024\n\022CapabilityExchange\032\022\n" +
+      "\020RestartWebServer\">\n\013RequestType\022\027\n\023CAPA" +
+      "BILITY_EXCHANGE\020\000\022\026\n\022RESTART_WEB_SERVER\020",
+      "\001\"\'\n\013ServiceType\022\n\n\006VIEWER\020\000\022\014\n\010DEV_MODE" +
+      "\020\001\032\305\r\n\010Response\022\021\n\trequestId\030\001 \002(\r\022Z\n\016vi" +
+      "ewerResponse\030\002 \001(\0132B.com.google.gwt.dev." +
+      "shell.remoteui.Message.Response.ViewerRe" +
+      "sponse\022\\\n\017devModeResponse\030\003 \001(\0132C.com.go" +
+      "ogle.gwt.dev.shell.remoteui.Message.Resp" +
+      "onse.DevModeResponse\032\265\006\n\016ViewerResponse\022" +
+      "e\n\014responseType\030\001 \002(\0162O.com.google.gwt.d" +
+      "ev.shell.remoteui.Message.Response.Viewe" +
+      "rResponse.ResponseType\022q\n\022capabilityExch",
+      "ange\030\002 \001(\0132U.com.google.gwt.dev.shell.re" +
+      "moteui.Message.Response.ViewerResponse.C" +
+      "apabilityExchange\022Y\n\006addLog\030\003 \001(\0132I.com." +
+      "google.gwt.dev.shell.remoteui.Message.Re" +
+      "sponse.ViewerResponse.AddLog\022e\n\014addLogBr" +
+      "anch\030\004 \001(\0132O.com.google.gwt.dev.shell.re" +
+      "moteui.Message.Response.ViewerResponse.A" +
+      "ddLogBranch\032\374\001\n\022CapabilityExchange\022v\n\014ca" +
+      "pabilities\030\002 \003(\0132`.com.google.gwt.dev.sh" +
+      "ell.remoteui.Message.Response.ViewerResp",
+      "onse.CapabilityExchange.Capability\032n\n\nCa" +
+      "pability\022`\n\ncapability\030\001 \002(\0162L.com.googl" +
+      "e.gwt.dev.shell.remoteui.Message.Request" +
+      ".ViewerRequest.RequestType\032\033\n\006AddLog\022\021\n\t" +
+      "logHandle\030\001 \002(\r\032!\n\014AddLogBranch\022\021\n\tlogHa" +
+      "ndle\030\001 \002(\r\"H\n\014ResponseType\022\027\n\023CAPABILITY" +
+      "_EXCHANGE\020\000\022\013\n\007ADD_LOG\020\001\022\022\n\016ADD_LOG_BRAN" +
+      "CH\020\002\032\263\005\n\017DevModeResponse\022f\n\014responseType" +
+      "\030\001 \002(\0162P.com.google.gwt.dev.shell.remote" +
+      "ui.Message.Response.DevModeResponse.Resp",
+      "onseType\022r\n\022capabilityExchange\030\002 \001(\0132V.c" +
+      "om.google.gwt.dev.shell.remoteui.Message" +
+      ".Response.DevModeResponse.CapabilityExch" +
+      "ange\022n\n\020restartWebServer\030\003 \001(\0132T.com.goo" +
+      "gle.gwt.dev.shell.remoteui.Message.Respo" +
+      "nse.DevModeResponse.RestartWebServer\032\376\001\n" +
+      "\022CapabilityExchange\022w\n\014capabilities\030\002 \003(" +
+      "\0132a.com.google.gwt.dev.shell.remoteui.Me" +
+      "ssage.Response.DevModeResponse.Capabilit" +
+      "yExchange.Capability\032o\n\nCapability\022a\n\nca",
+      "pability\030\001 \002(\0162M.com.google.gwt.dev.shel" +
+      "l.remoteui.Message.Request.DevModeReques" +
+      "t.RequestType\032\022\n\020RestartWebServer\"?\n\014Res" +
+      "ponseType\022\027\n\023CAPABILITY_EXCHANGE\020\000\022\026\n\022RE" +
+      "START_WEB_SERVER\020\001\"(\n\013MessageType\022\013\n\007REQ" +
+      "UEST\020\000\022\014\n\010RESPONSE\020\001B\024B\022RemoteMessagePro" +
+      "to"
+    };
+    com.google.gwt.dev.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner =
+      new com.google.gwt.dev.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner() {
+        public com.google.gwt.dev.protobuf.ExtensionRegistry assignDescriptors(
+            com.google.gwt.dev.protobuf.Descriptors.FileDescriptor root) {
+          descriptor = root;
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor =
+            getDescriptor().getMessageTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor,
+              new java.lang.String[] { "MessageType", "Request", "Response", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor,
+              new java.lang.String[] { "ServiceType", "RequestId", "ViewerRequest", "DevModeRequest", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor,
+              new java.lang.String[] { "RequestType", "CapabilityExchange", "AddLog", "AddLogBranch", "AddLogEntry", "DisconnectLog", "Initialize", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_CapabilityExchange_descriptor,
+              new java.lang.String[] { },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.CapabilityExchange.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor,
+              new java.lang.String[] { "Type", "ModuleLog", "ServerLog", "MainLog", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ModuleLog_descriptor,
+              new java.lang.String[] { "Name", "Icon", "SessionKey", "UserAgent", "Url", "TabKey", "RemoteHost", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ModuleLog.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_ServerLog_descriptor,
+              new java.lang.String[] { "Name", "Icon", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.ServerLog.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_descriptor.getNestedTypes().get(2);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLog_MainLog_descriptor,
+              new java.lang.String[] { },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLog.MainLog.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(2);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor,
+              new java.lang.String[] { "Summary", "Level", "Details", "HelpInfo", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_LogData_HelpInfo_descriptor,
+              new java.lang.String[] { "Url", "Text", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.LogData.HelpInfo.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(3);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogBranch_descriptor,
+              new java.lang.String[] { "ParentLogHandle", "IndexInParent", "LogData", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogBranch.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(4);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_AddLogEntry_descriptor,
+              new java.lang.String[] { "LogHandle", "IndexInLog", "LogData", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.AddLogEntry.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(5);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_DisconnectLog_descriptor,
+              new java.lang.String[] { "LogHandle", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.DisconnectLog.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_Initialize_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_descriptor.getNestedTypes().get(6);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_Initialize_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_ViewerRequest_Initialize_descriptor,
+              new java.lang.String[] { "ClientId", "DevModeQueryParam", "WebServerPort", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.ViewerRequest.Initialize.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor,
+              new java.lang.String[] { "RequestType", "CapabilityExchange", "RestartWebServer", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_CapabilityExchange_descriptor,
+              new java.lang.String[] { },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.CapabilityExchange.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Request_DevModeRequest_RestartWebServer_descriptor,
+              new java.lang.String[] { },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Request.DevModeRequest.RestartWebServer.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor,
+              new java.lang.String[] { "RequestId", "ViewerResponse", "DevModeResponse", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor,
+              new java.lang.String[] { "ResponseType", "CapabilityExchange", "AddLog", "AddLogBranch", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor,
+              new java.lang.String[] { "Capabilities", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_CapabilityExchange_Capability_descriptor,
+              new java.lang.String[] { "Capability", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.CapabilityExchange.Capability.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLog_descriptor,
+              new java.lang.String[] { "LogHandle", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLog.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_descriptor.getNestedTypes().get(2);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_ViewerResponse_AddLogBranch_descriptor,
+              new java.lang.String[] { "LogHandle", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.ViewerResponse.AddLogBranch.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor,
+              new java.lang.String[] { "ResponseType", "CapabilityExchange", "RestartWebServer", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor,
+              new java.lang.String[] { "Capabilities", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_descriptor.getNestedTypes().get(0);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_CapabilityExchange_Capability_descriptor,
+              new java.lang.String[] { "Capability", },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.CapabilityExchange.Capability.Builder.class);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor =
+            internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_descriptor.getNestedTypes().get(1);
+          internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_fieldAccessorTable = new
+            com.google.gwt.dev.protobuf.GeneratedMessage.FieldAccessorTable(
+              internal_static_com_google_gwt_dev_shell_remoteui_Message_Response_DevModeResponse_RestartWebServer_descriptor,
+              new java.lang.String[] { },
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.class,
+              com.google.gwt.dev.shell.remoteui.RemoteMessageProto.Message.Response.DevModeResponse.RestartWebServer.Builder.class);
+          return null;
+        }
+      };
+    com.google.gwt.dev.protobuf.Descriptors.FileDescriptor
+      .internalBuildGeneratedFileFrom(descriptorData,
+        new com.google.gwt.dev.protobuf.Descriptors.FileDescriptor[] {
+        }, assigner);
   }
-
-  public static void registerAllExtensions(
-      com.google.gwt.dev.protobuf.ExtensionRegistry registry) {
-  }
-
-  private RemoteMessageProto() {
-  }
+  
+  public static void internalForceInit() {}
 }
diff --git a/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteUI.java b/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteUI.java
index 0192843..420149c 100644
--- a/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteUI.java
+++ b/dev/core/src/com/google/gwt/dev/shell/remoteui/RemoteUI.java
@@ -17,6 +17,7 @@
 
 import com.google.gwt.core.ext.TreeLogger;
 import com.google.gwt.core.ext.TreeLogger.Type;
+import com.google.gwt.dev.shell.BrowserListener;
 import com.google.gwt.dev.ui.DevModeUI;
 import com.google.gwt.dev.ui.RestartServerCallback;
 import com.google.gwt.dev.ui.RestartServerEvent;
@@ -35,14 +36,22 @@
   private final List<ModuleHandle> modules = new ArrayList<ModuleHandle>();
   private final Object modulesLock = new Object();
 
+  private final String clientId;
   private final DevModeServiceRequestProcessor devModeRequestProcessor;
   private final MessageTransport transport;
   private ViewerServiceTreeLogger webServerLogger = null;
   private ViewerServiceTreeLogger mainLogger = null;
   private ViewerServiceClient viewerServiceClient = null;
+  private final int webServerPort;
+  private final int browserChannelPort;
 
-  public RemoteUI(String host, int port) {
+  public RemoteUI(String host, int port, String clientId, int webServerPort,
+      int browserChannelPort) {
     try {
+      this.clientId = clientId;
+      this.browserChannelPort = browserChannelPort;
+      this.webServerPort = webServerPort;
+
       Socket socket = new Socket(host, port);
       devModeRequestProcessor = new DevModeServiceRequestProcessor(this);
       transport = new MessageTransport(socket.getInputStream(),
@@ -85,6 +94,8 @@
   public void initialize(Type logLevel) {
     super.initialize(logLevel);
     viewerServiceClient = new ViewerServiceClient(transport);
+    String devModeQueryParam = BrowserListener.getDevModeURLParams(BrowserListener.computeEndpointIdentifier(browserChannelPort));
+    viewerServiceClient.initialize(clientId, devModeQueryParam, webServerPort);
     viewerServiceClient.checkCapabilities();
   }
 
diff --git a/dev/core/src/com/google/gwt/dev/shell/remoteui/ViewerServiceClient.java b/dev/core/src/com/google/gwt/dev/shell/remoteui/ViewerServiceClient.java
index 8ba127a..07010dd 100644
--- a/dev/core/src/com/google/gwt/dev/shell/remoteui/ViewerServiceClient.java
+++ b/dev/core/src/com/google/gwt/dev/shell/remoteui/ViewerServiceClient.java
@@ -207,7 +207,7 @@
 
     return createLogger(addLogBuilder);
   }
-
+  
   /**
    * Check the capabilities of the ViewerService. Ensures that the ViewerService
    * supports: adding a log, adding a log branch, adding a log entry, and
@@ -266,6 +266,22 @@
     waitForResponse(responseFuture);
   }
 
+  public void initialize(String clientId, String devModeQueryParam, int webServerPort) {
+    ViewerRequest.Initialize.Builder initializationBuilder = ViewerRequest.Initialize.newBuilder();
+    initializationBuilder.setClientId(clientId);
+    initializationBuilder.setDevModeQueryParam(devModeQueryParam);
+    initializationBuilder.setWebServerPort(webServerPort);
+    
+    ViewerRequest.Builder viewerRequestBuilder = ViewerRequest.newBuilder();
+    viewerRequestBuilder.setRequestType(ViewerRequest.RequestType.INITIALIZE);
+    viewerRequestBuilder.setInitialize(initializationBuilder);
+
+    Request.Builder request = buildRequestMessageFromViewerRequest(viewerRequestBuilder);
+
+    Future<Response> responseFuture = transport.executeRequestAsync(request.build());
+    waitForResponse(responseFuture);
+  }
+
   private Request.Builder buildRequestMessageFromViewerRequest(
       ViewerRequest.Builder viewerRequestBuilder) {
     return Request.newBuilder().setServiceType(Request.ServiceType.VIEWER).setViewerRequest(
diff --git a/dev/core/src/com/google/gwt/dev/shell/remoteui/remotemessage.proto b/dev/core/src/com/google/gwt/dev/shell/remoteui/remotemessage.proto
index cb880c7..f693b33 100644
--- a/dev/core/src/com/google/gwt/dev/shell/remoteui/remotemessage.proto
+++ b/dev/core/src/com/google/gwt/dev/shell/remoteui/remotemessage.proto
@@ -47,7 +47,8 @@
         ADD_LOG = 1;
         ADD_LOG_BRANCH = 2;
         ADD_LOG_ENTRY = 3;
-        DISCONNECT_LOG = 4;        
+        DISCONNECT_LOG = 4;
+        INITIALIZE = 5;        
       }
       
       // Request the capabilities of the ViewerService. No additional
@@ -129,12 +130,19 @@
         required uint32 logHandle = 1;
       }
       
+      message Initialize {
+        optional string clientId = 1;
+        optional string devModeQueryParam = 2;
+        optional sint32 webServerPort = 3;         
+      }
+      
       required RequestType requestType = 1;
       optional CapabilityExchange capabilityExchange = 2;
       optional AddLog addLog = 3;
       optional AddLogBranch addLogBranch = 4;
       optional AddLogEntry addLogEntry = 5;
-      optional DisconnectLog disconnectLog = 6;                 
+      optional DisconnectLog disconnectLog = 6;
+      optional Initialize initialize = 7;                 
     }
   
     // The root type for all requests for the DevModeService
