Project import
diff --git a/LICENSE b/LICENSE
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/LICENSE
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..cb2900d
--- /dev/null
+++ b/README.md
@@ -0,0 +1,26 @@
+What is this, exactly?
+======================
+* An Objective-C interface (src/runtime) for creating and reading protobuf messages.
+* Source for Obj-C protobuf compiler (src/compiler), which allows us to compile protobuf source (.proto) into compiled Obj-C source. This is built and installed as protoc-gen-objc.
+* A number of .proto files (src/proto) that define the interface we use when interfacing with Dropcam devices and certain services. These are compiled using the compiler.
+* A script (compile_proto.sh) which generates the compiled Obj-C source and places it in src/gen_proto.
+
+Prerequisites
+=============
+* Homebrew, to install the following dependencies. Installing it to ~/homebrew is suggested. See https://wiki.corp.google.com/twiki/bin/view/Main/MacRoadWarrior#Homebrew for more details. No matter where you install it, set HOMEBREW to the root Homebrew directory.
+* Protobuf, to compile the Obj-C compiler. Protobuf 2.6.0 is requried and as of this writing, it is the current version provided via Homebrew.
+* autoconf, to run the autogen script.
+
+`brew install protobuf`
+
+`brew install autoconf automake libevent libtool`
+
+Generating Compiled Protobuf Source
+=====================================
+`./compile_proto.sh`
+
+How does it work?
+=================
+* compile_proto.sh runs build.sh
+* build.sh builds protoc-gen-objc, the Obj-C protbuf compiler, and installs it in bin.
+* Then, compile_proto.sh runs protoc, the generic protobuf compiler provided by protobuf, using protoc-gen-objc as a plugin. All .proto source in src/proto is compiled into Obj-C, and is output to src/gen_proto.
diff --git a/src/gen_proto/Account_info.pb.h b/src/gen_proto/Account_info.pb.h
new file mode 100644
index 0000000..8111915
--- /dev/null
+++ b/src/gen_proto/Account_info.pb.h
@@ -0,0 +1,87 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class AccountInfo;
+@class AccountInfoBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+
+@interface AccountInfoRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface AccountInfo : PBGeneratedMessage {
+@private
+  BOOL hasUserId_:1;
+  BOOL hasStructureId_:1;
+  NSString* userId;
+  NSString* structureId;
+}
+- (BOOL) hasUserId;
+- (BOOL) hasStructureId;
+@property (readonly, strong) NSString* userId;
+@property (readonly, strong) NSString* structureId;
+
++ (AccountInfo*) defaultInstance;
+- (AccountInfo*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (AccountInfoBuilder*) builder;
++ (AccountInfoBuilder*) builder;
++ (AccountInfoBuilder*) builderWithPrototype:(AccountInfo*) prototype;
+- (AccountInfoBuilder*) toBuilder;
+
++ (AccountInfo*) parseFromData:(NSData*) data;
++ (AccountInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (AccountInfo*) parseFromInputStream:(NSInputStream*) input;
++ (AccountInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (AccountInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (AccountInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface AccountInfoBuilder : PBGeneratedMessageBuilder {
+@private
+  AccountInfo* result;
+}
+
+- (AccountInfo*) defaultInstance;
+
+- (AccountInfoBuilder*) clear;
+- (AccountInfoBuilder*) clone;
+
+- (AccountInfo*) build;
+- (AccountInfo*) buildPartial;
+
+- (AccountInfoBuilder*) mergeFrom:(AccountInfo*) other;
+- (AccountInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (AccountInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasUserId;
+- (NSString*) userId;
+- (AccountInfoBuilder*) setUserId:(NSString*) value;
+- (AccountInfoBuilder*) clearUserId;
+
+- (BOOL) hasStructureId;
+- (NSString*) structureId;
+- (AccountInfoBuilder*) setStructureId:(NSString*) value;
+- (AccountInfoBuilder*) clearStructureId;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Account_info.pb.m b/src/gen_proto/Account_info.pb.m
new file mode 100644
index 0000000..e90af02
--- /dev/null
+++ b/src/gen_proto/Account_info.pb.m
@@ -0,0 +1,270 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Account_info.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation AccountInfoRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [AccountInfoRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface AccountInfo ()
+@property (strong) NSString* userId;
+@property (strong) NSString* structureId;
+@end
+
+@implementation AccountInfo
+
+- (BOOL) hasUserId {
+  return !!hasUserId_;
+}
+- (void) setHasUserId:(BOOL) value_ {
+  hasUserId_ = !!value_;
+}
+@synthesize userId;
+- (BOOL) hasStructureId {
+  return !!hasStructureId_;
+}
+- (void) setHasStructureId:(BOOL) value_ {
+  hasStructureId_ = !!value_;
+}
+@synthesize structureId;
+- (id) init {
+  if ((self = [super init])) {
+    self.userId = @"";
+    self.structureId = @"";
+  }
+  return self;
+}
+static AccountInfo* defaultAccountInfoInstance = nil;
++ (void) initialize {
+  if (self == [AccountInfo class]) {
+    defaultAccountInfoInstance = [[AccountInfo alloc] init];
+  }
+}
++ (AccountInfo*) defaultInstance {
+  return defaultAccountInfoInstance;
+}
+- (AccountInfo*) defaultInstance {
+  return defaultAccountInfoInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasUserId) {
+    [output writeString:1 value:self.userId];
+  }
+  if (self.hasStructureId) {
+    [output writeString:2 value:self.structureId];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasUserId) {
+    size_ += computeStringSize(1, self.userId);
+  }
+  if (self.hasStructureId) {
+    size_ += computeStringSize(2, self.structureId);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (AccountInfo*) parseFromData:(NSData*) data {
+  return (AccountInfo*)[[[AccountInfo builder] mergeFromData:data] build];
+}
++ (AccountInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AccountInfo*)[[[AccountInfo builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (AccountInfo*) parseFromInputStream:(NSInputStream*) input {
+  return (AccountInfo*)[[[AccountInfo builder] mergeFromInputStream:input] build];
+}
++ (AccountInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AccountInfo*)[[[AccountInfo builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (AccountInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (AccountInfo*)[[[AccountInfo builder] mergeFromCodedInputStream:input] build];
+}
++ (AccountInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AccountInfo*)[[[AccountInfo builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (AccountInfoBuilder*) builder {
+  return [[AccountInfoBuilder alloc] init];
+}
++ (AccountInfoBuilder*) builderWithPrototype:(AccountInfo*) prototype {
+  return [[AccountInfo builder] mergeFrom:prototype];
+}
+- (AccountInfoBuilder*) builder {
+  return [AccountInfo builder];
+}
+- (AccountInfoBuilder*) toBuilder {
+  return [AccountInfo builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasUserId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"userId", self.userId];
+  }
+  if (self.hasStructureId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"structureId", self.structureId];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[AccountInfo class]]) {
+    return NO;
+  }
+  AccountInfo *otherMessage = other;
+  return
+      self.hasUserId == otherMessage.hasUserId &&
+      (!self.hasUserId || [self.userId isEqual:otherMessage.userId]) &&
+      self.hasStructureId == otherMessage.hasStructureId &&
+      (!self.hasStructureId || [self.structureId isEqual:otherMessage.structureId]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasUserId) {
+    hashCode = hashCode * 31 + [self.userId hash];
+  }
+  if (self.hasStructureId) {
+    hashCode = hashCode * 31 + [self.structureId hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface AccountInfoBuilder()
+@property (strong) AccountInfo* result;
+@end
+
+@implementation AccountInfoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[AccountInfo alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (AccountInfoBuilder*) clear {
+  self.result = [[AccountInfo alloc] init];
+  return self;
+}
+- (AccountInfoBuilder*) clone {
+  return [AccountInfo builderWithPrototype:result];
+}
+- (AccountInfo*) defaultInstance {
+  return [AccountInfo defaultInstance];
+}
+- (AccountInfo*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (AccountInfo*) buildPartial {
+  AccountInfo* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (AccountInfoBuilder*) mergeFrom:(AccountInfo*) other {
+  if (other == [AccountInfo defaultInstance]) {
+    return self;
+  }
+  if (other.hasUserId) {
+    [self setUserId:other.userId];
+  }
+  if (other.hasStructureId) {
+    [self setStructureId:other.structureId];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (AccountInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (AccountInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setUserId:[input readString]];
+        break;
+      }
+      case 18: {
+        [self setStructureId:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasUserId {
+  return result.hasUserId;
+}
+- (NSString*) userId {
+  return result.userId;
+}
+- (AccountInfoBuilder*) setUserId:(NSString*) value {
+  result.hasUserId = YES;
+  result.userId = value;
+  return self;
+}
+- (AccountInfoBuilder*) clearUserId {
+  result.hasUserId = NO;
+  result.userId = @"";
+  return self;
+}
+- (BOOL) hasStructureId {
+  return result.hasStructureId;
+}
+- (NSString*) structureId {
+  return result.structureId;
+}
+- (AccountInfoBuilder*) setStructureId:(NSString*) value {
+  result.hasStructureId = YES;
+  result.structureId = value;
+  return self;
+}
+- (AccountInfoBuilder*) clearStructureId {
+  result.hasStructureId = NO;
+  result.structureId = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/App_log.pb.h b/src/gen_proto/App_log.pb.h
new file mode 100644
index 0000000..0b4ee02
--- /dev/null
+++ b/src/gen_proto/App_log.pb.h
@@ -0,0 +1,97 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+#import "Weave_pairing_session_log.pb.h"
+// @@protoc_insertion_point(imports)
+
+@class AccountInfo;
+@class AccountInfoBuilder;
+@class AppLog;
+@class AppLogBuilder;
+@class Environment;
+@class EnvironmentBuilder;
+@class Event;
+@class EventBuilder;
+@class FabricInfo;
+@class FabricInfoBuilder;
+@class IdentificationProfile;
+@class IdentificationProfileBuilder;
+@class Pair;
+@class PairBuilder;
+@class SoftwareProfile;
+@class SoftwareProfileBuilder;
+@class WeavePairingSessionLog;
+@class WeavePairingSessionLogBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+
+@interface AppLogRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface AppLog : PBGeneratedMessage {
+@private
+  BOOL hasWeavePairingSessionLog_:1;
+  WeavePairingSessionLog* weavePairingSessionLog;
+}
+- (BOOL) hasWeavePairingSessionLog;
+@property (readonly, strong) WeavePairingSessionLog* weavePairingSessionLog;
+
++ (AppLog*) defaultInstance;
+- (AppLog*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (AppLogBuilder*) builder;
++ (AppLogBuilder*) builder;
++ (AppLogBuilder*) builderWithPrototype:(AppLog*) prototype;
+- (AppLogBuilder*) toBuilder;
+
++ (AppLog*) parseFromData:(NSData*) data;
++ (AppLog*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (AppLog*) parseFromInputStream:(NSInputStream*) input;
++ (AppLog*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (AppLog*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (AppLog*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface AppLogBuilder : PBGeneratedMessageBuilder {
+@private
+  AppLog* result;
+}
+
+- (AppLog*) defaultInstance;
+
+- (AppLogBuilder*) clear;
+- (AppLogBuilder*) clone;
+
+- (AppLog*) build;
+- (AppLog*) buildPartial;
+
+- (AppLogBuilder*) mergeFrom:(AppLog*) other;
+- (AppLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (AppLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasWeavePairingSessionLog;
+- (WeavePairingSessionLog*) weavePairingSessionLog;
+- (AppLogBuilder*) setWeavePairingSessionLog:(WeavePairingSessionLog*) value;
+- (AppLogBuilder*) setWeavePairingSessionLogBuilder:(WeavePairingSessionLogBuilder*) builderForValue;
+- (AppLogBuilder*) mergeWeavePairingSessionLog:(WeavePairingSessionLog*) value;
+- (AppLogBuilder*) clearWeavePairingSessionLog;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/App_log.pb.m b/src/gen_proto/App_log.pb.m
new file mode 100644
index 0000000..b5cf327
--- /dev/null
+++ b/src/gen_proto/App_log.pb.m
@@ -0,0 +1,247 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "App_log.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation AppLogRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [AppLogRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    [WeavePairingSessionLogRoot registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface AppLog ()
+@property (strong) WeavePairingSessionLog* weavePairingSessionLog;
+@end
+
+@implementation AppLog
+
+- (BOOL) hasWeavePairingSessionLog {
+  return !!hasWeavePairingSessionLog_;
+}
+- (void) setHasWeavePairingSessionLog:(BOOL) value_ {
+  hasWeavePairingSessionLog_ = !!value_;
+}
+@synthesize weavePairingSessionLog;
+- (id) init {
+  if ((self = [super init])) {
+    self.weavePairingSessionLog = [WeavePairingSessionLog defaultInstance];
+  }
+  return self;
+}
+static AppLog* defaultAppLogInstance = nil;
++ (void) initialize {
+  if (self == [AppLog class]) {
+    defaultAppLogInstance = [[AppLog alloc] init];
+  }
+}
++ (AppLog*) defaultInstance {
+  return defaultAppLogInstance;
+}
+- (AppLog*) defaultInstance {
+  return defaultAppLogInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasWeavePairingSessionLog) {
+    [output writeMessage:1 value:self.weavePairingSessionLog];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasWeavePairingSessionLog) {
+    size_ += computeMessageSize(1, self.weavePairingSessionLog);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (AppLog*) parseFromData:(NSData*) data {
+  return (AppLog*)[[[AppLog builder] mergeFromData:data] build];
+}
++ (AppLog*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AppLog*)[[[AppLog builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (AppLog*) parseFromInputStream:(NSInputStream*) input {
+  return (AppLog*)[[[AppLog builder] mergeFromInputStream:input] build];
+}
++ (AppLog*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AppLog*)[[[AppLog builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (AppLog*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (AppLog*)[[[AppLog builder] mergeFromCodedInputStream:input] build];
+}
++ (AppLog*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AppLog*)[[[AppLog builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (AppLogBuilder*) builder {
+  return [[AppLogBuilder alloc] init];
+}
++ (AppLogBuilder*) builderWithPrototype:(AppLog*) prototype {
+  return [[AppLog builder] mergeFrom:prototype];
+}
+- (AppLogBuilder*) builder {
+  return [AppLog builder];
+}
+- (AppLogBuilder*) toBuilder {
+  return [AppLog builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasWeavePairingSessionLog) {
+    [output appendFormat:@"%@%@ {\n", indent, @"weavePairingSessionLog"];
+    [self.weavePairingSessionLog writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[AppLog class]]) {
+    return NO;
+  }
+  AppLog *otherMessage = other;
+  return
+      self.hasWeavePairingSessionLog == otherMessage.hasWeavePairingSessionLog &&
+      (!self.hasWeavePairingSessionLog || [self.weavePairingSessionLog isEqual:otherMessage.weavePairingSessionLog]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasWeavePairingSessionLog) {
+    hashCode = hashCode * 31 + [self.weavePairingSessionLog hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface AppLogBuilder()
+@property (strong) AppLog* result;
+@end
+
+@implementation AppLogBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[AppLog alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (AppLogBuilder*) clear {
+  self.result = [[AppLog alloc] init];
+  return self;
+}
+- (AppLogBuilder*) clone {
+  return [AppLog builderWithPrototype:result];
+}
+- (AppLog*) defaultInstance {
+  return [AppLog defaultInstance];
+}
+- (AppLog*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (AppLog*) buildPartial {
+  AppLog* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (AppLogBuilder*) mergeFrom:(AppLog*) other {
+  if (other == [AppLog defaultInstance]) {
+    return self;
+  }
+  if (other.hasWeavePairingSessionLog) {
+    [self mergeWeavePairingSessionLog:other.weavePairingSessionLog];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (AppLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (AppLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        WeavePairingSessionLogBuilder* subBuilder = [WeavePairingSessionLog builder];
+        if (self.hasWeavePairingSessionLog) {
+          [subBuilder mergeFrom:self.weavePairingSessionLog];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setWeavePairingSessionLog:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasWeavePairingSessionLog {
+  return result.hasWeavePairingSessionLog;
+}
+- (WeavePairingSessionLog*) weavePairingSessionLog {
+  return result.weavePairingSessionLog;
+}
+- (AppLogBuilder*) setWeavePairingSessionLog:(WeavePairingSessionLog*) value {
+  result.hasWeavePairingSessionLog = YES;
+  result.weavePairingSessionLog = value;
+  return self;
+}
+- (AppLogBuilder*) setWeavePairingSessionLogBuilder:(WeavePairingSessionLogBuilder*) builderForValue {
+  return [self setWeavePairingSessionLog:[builderForValue build]];
+}
+- (AppLogBuilder*) mergeWeavePairingSessionLog:(WeavePairingSessionLog*) value {
+  if (result.hasWeavePairingSessionLog &&
+      result.weavePairingSessionLog != [WeavePairingSessionLog defaultInstance]) {
+    result.weavePairingSessionLog =
+      [[[WeavePairingSessionLog builderWithPrototype:result.weavePairingSessionLog] mergeFrom:value] buildPartial];
+  } else {
+    result.weavePairingSessionLog = value;
+  }
+  result.hasWeavePairingSessionLog = YES;
+  return self;
+}
+- (AppLogBuilder*) clearWeavePairingSessionLog {
+  result.hasWeavePairingSessionLog = NO;
+  result.weavePairingSessionLog = [WeavePairingSessionLog defaultInstance];
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Commontalk.pb.h b/src/gen_proto/Commontalk.pb.h
new file mode 100644
index 0000000..33ac89b
--- /dev/null
+++ b/src/gen_proto/Commontalk.pb.h
@@ -0,0 +1,42 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  CT_AVProfileAudioAac = 3,
+  CT_AVProfileAudioSpeex = 4,
+  CT_AVProfileAudioOpus = 5,
+  CT_AVProfileVideoH26450KbitL12 = 6,
+  CT_AVProfileVideoH264530KbitL31 = 7,
+  CT_AVProfileVideoH264100KbitL30 = 8,
+  CT_AVProfileVideoH2642MbitL40 = 9,
+  CT_AVProfileVideoH26450KbitL12Thumbnail = 10,
+  CT_AVProfileAvprofileMobile1 = 1,
+  CT_AVProfileAvprofileHdMain1 = 2,
+} CT_AVProfile;
+
+BOOL CT_AVProfileIsValidValue(CT_AVProfile value);
+
+
+@interface CommontalkRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Commontalk.pb.m b/src/gen_proto/Commontalk.pb.m
new file mode 100644
index 0000000..0c268ae
--- /dev/null
+++ b/src/gen_proto/Commontalk.pb.m
@@ -0,0 +1,41 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Commontalk.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation CommontalkRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [CommontalkRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+BOOL CT_AVProfileIsValidValue(CT_AVProfile value) {
+  switch (value) {
+    case CT_AVProfileAudioAac:
+    case CT_AVProfileAudioSpeex:
+    case CT_AVProfileAudioOpus:
+    case CT_AVProfileVideoH26450KbitL12:
+    case CT_AVProfileVideoH264530KbitL31:
+    case CT_AVProfileVideoH264100KbitL30:
+    case CT_AVProfileVideoH2642MbitL40:
+    case CT_AVProfileVideoH26450KbitL12Thumbnail:
+    case CT_AVProfileAvprofileMobile1:
+    case CT_AVProfileAvprofileHdMain1:
+      return YES;
+    default:
+      return NO;
+  }
+}
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Environment.pb.h b/src/gen_proto/Environment.pb.h
new file mode 100644
index 0000000..ff5522f
--- /dev/null
+++ b/src/gen_proto/Environment.pb.h
@@ -0,0 +1,140 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class Environment;
+@class EnvironmentBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  EnvironmentOSUnknown = 0,
+  EnvironmentOSAndroid = 1,
+  EnvironmentOSIos = 2,
+} EnvironmentOS;
+
+BOOL EnvironmentOSIsValidValue(EnvironmentOS value);
+
+
+@interface EnvironmentRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface Environment : PBGeneratedMessage {
+@private
+  BOOL hasAppVersion_:1;
+  BOOL hasAppVariant_:1;
+  BOOL hasOsVersion_:1;
+  BOOL hasBuildModel_:1;
+  BOOL hasBuildManufacturer_:1;
+  BOOL hasMobileCarrier_:1;
+  BOOL hasOsType_:1;
+  NSString* appVersion;
+  NSString* appVariant;
+  NSString* osVersion;
+  NSString* buildModel;
+  NSString* buildManufacturer;
+  NSString* mobileCarrier;
+  EnvironmentOS osType;
+}
+- (BOOL) hasAppVersion;
+- (BOOL) hasAppVariant;
+- (BOOL) hasOsType;
+- (BOOL) hasOsVersion;
+- (BOOL) hasBuildModel;
+- (BOOL) hasBuildManufacturer;
+- (BOOL) hasMobileCarrier;
+@property (readonly, strong) NSString* appVersion;
+@property (readonly, strong) NSString* appVariant;
+@property (readonly) EnvironmentOS osType;
+@property (readonly, strong) NSString* osVersion;
+@property (readonly, strong) NSString* buildModel;
+@property (readonly, strong) NSString* buildManufacturer;
+@property (readonly, strong) NSString* mobileCarrier;
+
++ (Environment*) defaultInstance;
+- (Environment*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (EnvironmentBuilder*) builder;
++ (EnvironmentBuilder*) builder;
++ (EnvironmentBuilder*) builderWithPrototype:(Environment*) prototype;
+- (EnvironmentBuilder*) toBuilder;
+
++ (Environment*) parseFromData:(NSData*) data;
++ (Environment*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Environment*) parseFromInputStream:(NSInputStream*) input;
++ (Environment*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Environment*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Environment*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface EnvironmentBuilder : PBGeneratedMessageBuilder {
+@private
+  Environment* result;
+}
+
+- (Environment*) defaultInstance;
+
+- (EnvironmentBuilder*) clear;
+- (EnvironmentBuilder*) clone;
+
+- (Environment*) build;
+- (Environment*) buildPartial;
+
+- (EnvironmentBuilder*) mergeFrom:(Environment*) other;
+- (EnvironmentBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (EnvironmentBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasAppVersion;
+- (NSString*) appVersion;
+- (EnvironmentBuilder*) setAppVersion:(NSString*) value;
+- (EnvironmentBuilder*) clearAppVersion;
+
+- (BOOL) hasAppVariant;
+- (NSString*) appVariant;
+- (EnvironmentBuilder*) setAppVariant:(NSString*) value;
+- (EnvironmentBuilder*) clearAppVariant;
+
+- (BOOL) hasOsType;
+- (EnvironmentOS) osType;
+- (EnvironmentBuilder*) setOsType:(EnvironmentOS) value;
+- (EnvironmentBuilder*) clearOsType;
+
+- (BOOL) hasOsVersion;
+- (NSString*) osVersion;
+- (EnvironmentBuilder*) setOsVersion:(NSString*) value;
+- (EnvironmentBuilder*) clearOsVersion;
+
+- (BOOL) hasBuildModel;
+- (NSString*) buildModel;
+- (EnvironmentBuilder*) setBuildModel:(NSString*) value;
+- (EnvironmentBuilder*) clearBuildModel;
+
+- (BOOL) hasBuildManufacturer;
+- (NSString*) buildManufacturer;
+- (EnvironmentBuilder*) setBuildManufacturer:(NSString*) value;
+- (EnvironmentBuilder*) clearBuildManufacturer;
+
+- (BOOL) hasMobileCarrier;
+- (NSString*) mobileCarrier;
+- (EnvironmentBuilder*) setMobileCarrier:(NSString*) value;
+- (EnvironmentBuilder*) clearMobileCarrier;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Environment.pb.m b/src/gen_proto/Environment.pb.m
new file mode 100644
index 0000000..9a38f22
--- /dev/null
+++ b/src/gen_proto/Environment.pb.m
@@ -0,0 +1,515 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Environment.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation EnvironmentRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [EnvironmentRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface Environment ()
+@property (strong) NSString* appVersion;
+@property (strong) NSString* appVariant;
+@property EnvironmentOS osType;
+@property (strong) NSString* osVersion;
+@property (strong) NSString* buildModel;
+@property (strong) NSString* buildManufacturer;
+@property (strong) NSString* mobileCarrier;
+@end
+
+@implementation Environment
+
+- (BOOL) hasAppVersion {
+  return !!hasAppVersion_;
+}
+- (void) setHasAppVersion:(BOOL) value_ {
+  hasAppVersion_ = !!value_;
+}
+@synthesize appVersion;
+- (BOOL) hasAppVariant {
+  return !!hasAppVariant_;
+}
+- (void) setHasAppVariant:(BOOL) value_ {
+  hasAppVariant_ = !!value_;
+}
+@synthesize appVariant;
+- (BOOL) hasOsType {
+  return !!hasOsType_;
+}
+- (void) setHasOsType:(BOOL) value_ {
+  hasOsType_ = !!value_;
+}
+@synthesize osType;
+- (BOOL) hasOsVersion {
+  return !!hasOsVersion_;
+}
+- (void) setHasOsVersion:(BOOL) value_ {
+  hasOsVersion_ = !!value_;
+}
+@synthesize osVersion;
+- (BOOL) hasBuildModel {
+  return !!hasBuildModel_;
+}
+- (void) setHasBuildModel:(BOOL) value_ {
+  hasBuildModel_ = !!value_;
+}
+@synthesize buildModel;
+- (BOOL) hasBuildManufacturer {
+  return !!hasBuildManufacturer_;
+}
+- (void) setHasBuildManufacturer:(BOOL) value_ {
+  hasBuildManufacturer_ = !!value_;
+}
+@synthesize buildManufacturer;
+- (BOOL) hasMobileCarrier {
+  return !!hasMobileCarrier_;
+}
+- (void) setHasMobileCarrier:(BOOL) value_ {
+  hasMobileCarrier_ = !!value_;
+}
+@synthesize mobileCarrier;
+- (id) init {
+  if ((self = [super init])) {
+    self.appVersion = @"";
+    self.appVariant = @"";
+    self.osType = EnvironmentOSUnknown;
+    self.osVersion = @"";
+    self.buildModel = @"";
+    self.buildManufacturer = @"";
+    self.mobileCarrier = @"";
+  }
+  return self;
+}
+static Environment* defaultEnvironmentInstance = nil;
++ (void) initialize {
+  if (self == [Environment class]) {
+    defaultEnvironmentInstance = [[Environment alloc] init];
+  }
+}
++ (Environment*) defaultInstance {
+  return defaultEnvironmentInstance;
+}
+- (Environment*) defaultInstance {
+  return defaultEnvironmentInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasAppVersion) {
+    [output writeString:1 value:self.appVersion];
+  }
+  if (self.hasAppVariant) {
+    [output writeString:2 value:self.appVariant];
+  }
+  if (self.hasOsType) {
+    [output writeEnum:3 value:self.osType];
+  }
+  if (self.hasOsVersion) {
+    [output writeString:4 value:self.osVersion];
+  }
+  if (self.hasBuildModel) {
+    [output writeString:5 value:self.buildModel];
+  }
+  if (self.hasBuildManufacturer) {
+    [output writeString:6 value:self.buildManufacturer];
+  }
+  if (self.hasMobileCarrier) {
+    [output writeString:7 value:self.mobileCarrier];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasAppVersion) {
+    size_ += computeStringSize(1, self.appVersion);
+  }
+  if (self.hasAppVariant) {
+    size_ += computeStringSize(2, self.appVariant);
+  }
+  if (self.hasOsType) {
+    size_ += computeEnumSize(3, self.osType);
+  }
+  if (self.hasOsVersion) {
+    size_ += computeStringSize(4, self.osVersion);
+  }
+  if (self.hasBuildModel) {
+    size_ += computeStringSize(5, self.buildModel);
+  }
+  if (self.hasBuildManufacturer) {
+    size_ += computeStringSize(6, self.buildManufacturer);
+  }
+  if (self.hasMobileCarrier) {
+    size_ += computeStringSize(7, self.mobileCarrier);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Environment*) parseFromData:(NSData*) data {
+  return (Environment*)[[[Environment builder] mergeFromData:data] build];
+}
++ (Environment*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Environment*)[[[Environment builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Environment*) parseFromInputStream:(NSInputStream*) input {
+  return (Environment*)[[[Environment builder] mergeFromInputStream:input] build];
+}
++ (Environment*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Environment*)[[[Environment builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Environment*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Environment*)[[[Environment builder] mergeFromCodedInputStream:input] build];
+}
++ (Environment*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Environment*)[[[Environment builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (EnvironmentBuilder*) builder {
+  return [[EnvironmentBuilder alloc] init];
+}
++ (EnvironmentBuilder*) builderWithPrototype:(Environment*) prototype {
+  return [[Environment builder] mergeFrom:prototype];
+}
+- (EnvironmentBuilder*) builder {
+  return [Environment builder];
+}
+- (EnvironmentBuilder*) toBuilder {
+  return [Environment builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasAppVersion) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"appVersion", self.appVersion];
+  }
+  if (self.hasAppVariant) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"appVariant", self.appVariant];
+  }
+  if (self.hasOsType) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"osType", self.osType];
+  }
+  if (self.hasOsVersion) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"osVersion", self.osVersion];
+  }
+  if (self.hasBuildModel) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"buildModel", self.buildModel];
+  }
+  if (self.hasBuildManufacturer) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"buildManufacturer", self.buildManufacturer];
+  }
+  if (self.hasMobileCarrier) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"mobileCarrier", self.mobileCarrier];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Environment class]]) {
+    return NO;
+  }
+  Environment *otherMessage = other;
+  return
+      self.hasAppVersion == otherMessage.hasAppVersion &&
+      (!self.hasAppVersion || [self.appVersion isEqual:otherMessage.appVersion]) &&
+      self.hasAppVariant == otherMessage.hasAppVariant &&
+      (!self.hasAppVariant || [self.appVariant isEqual:otherMessage.appVariant]) &&
+      self.hasOsType == otherMessage.hasOsType &&
+      (!self.hasOsType || self.osType == otherMessage.osType) &&
+      self.hasOsVersion == otherMessage.hasOsVersion &&
+      (!self.hasOsVersion || [self.osVersion isEqual:otherMessage.osVersion]) &&
+      self.hasBuildModel == otherMessage.hasBuildModel &&
+      (!self.hasBuildModel || [self.buildModel isEqual:otherMessage.buildModel]) &&
+      self.hasBuildManufacturer == otherMessage.hasBuildManufacturer &&
+      (!self.hasBuildManufacturer || [self.buildManufacturer isEqual:otherMessage.buildManufacturer]) &&
+      self.hasMobileCarrier == otherMessage.hasMobileCarrier &&
+      (!self.hasMobileCarrier || [self.mobileCarrier isEqual:otherMessage.mobileCarrier]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasAppVersion) {
+    hashCode = hashCode * 31 + [self.appVersion hash];
+  }
+  if (self.hasAppVariant) {
+    hashCode = hashCode * 31 + [self.appVariant hash];
+  }
+  if (self.hasOsType) {
+    hashCode = hashCode * 31 + self.osType;
+  }
+  if (self.hasOsVersion) {
+    hashCode = hashCode * 31 + [self.osVersion hash];
+  }
+  if (self.hasBuildModel) {
+    hashCode = hashCode * 31 + [self.buildModel hash];
+  }
+  if (self.hasBuildManufacturer) {
+    hashCode = hashCode * 31 + [self.buildManufacturer hash];
+  }
+  if (self.hasMobileCarrier) {
+    hashCode = hashCode * 31 + [self.mobileCarrier hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL EnvironmentOSIsValidValue(EnvironmentOS value) {
+  switch (value) {
+    case EnvironmentOSUnknown:
+    case EnvironmentOSAndroid:
+    case EnvironmentOSIos:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface EnvironmentBuilder()
+@property (strong) Environment* result;
+@end
+
+@implementation EnvironmentBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Environment alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (EnvironmentBuilder*) clear {
+  self.result = [[Environment alloc] init];
+  return self;
+}
+- (EnvironmentBuilder*) clone {
+  return [Environment builderWithPrototype:result];
+}
+- (Environment*) defaultInstance {
+  return [Environment defaultInstance];
+}
+- (Environment*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Environment*) buildPartial {
+  Environment* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (EnvironmentBuilder*) mergeFrom:(Environment*) other {
+  if (other == [Environment defaultInstance]) {
+    return self;
+  }
+  if (other.hasAppVersion) {
+    [self setAppVersion:other.appVersion];
+  }
+  if (other.hasAppVariant) {
+    [self setAppVariant:other.appVariant];
+  }
+  if (other.hasOsType) {
+    [self setOsType:other.osType];
+  }
+  if (other.hasOsVersion) {
+    [self setOsVersion:other.osVersion];
+  }
+  if (other.hasBuildModel) {
+    [self setBuildModel:other.buildModel];
+  }
+  if (other.hasBuildManufacturer) {
+    [self setBuildManufacturer:other.buildManufacturer];
+  }
+  if (other.hasMobileCarrier) {
+    [self setMobileCarrier:other.mobileCarrier];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (EnvironmentBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (EnvironmentBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setAppVersion:[input readString]];
+        break;
+      }
+      case 18: {
+        [self setAppVariant:[input readString]];
+        break;
+      }
+      case 24: {
+        EnvironmentOS value = (EnvironmentOS)[input readEnum];
+        if (EnvironmentOSIsValidValue(value)) {
+          [self setOsType:value];
+        } else {
+          [unknownFields mergeVarintField:3 value:value];
+        }
+        break;
+      }
+      case 34: {
+        [self setOsVersion:[input readString]];
+        break;
+      }
+      case 42: {
+        [self setBuildModel:[input readString]];
+        break;
+      }
+      case 50: {
+        [self setBuildManufacturer:[input readString]];
+        break;
+      }
+      case 58: {
+        [self setMobileCarrier:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasAppVersion {
+  return result.hasAppVersion;
+}
+- (NSString*) appVersion {
+  return result.appVersion;
+}
+- (EnvironmentBuilder*) setAppVersion:(NSString*) value {
+  result.hasAppVersion = YES;
+  result.appVersion = value;
+  return self;
+}
+- (EnvironmentBuilder*) clearAppVersion {
+  result.hasAppVersion = NO;
+  result.appVersion = @"";
+  return self;
+}
+- (BOOL) hasAppVariant {
+  return result.hasAppVariant;
+}
+- (NSString*) appVariant {
+  return result.appVariant;
+}
+- (EnvironmentBuilder*) setAppVariant:(NSString*) value {
+  result.hasAppVariant = YES;
+  result.appVariant = value;
+  return self;
+}
+- (EnvironmentBuilder*) clearAppVariant {
+  result.hasAppVariant = NO;
+  result.appVariant = @"";
+  return self;
+}
+- (BOOL) hasOsType {
+  return result.hasOsType;
+}
+- (EnvironmentOS) osType {
+  return result.osType;
+}
+- (EnvironmentBuilder*) setOsType:(EnvironmentOS) value {
+  result.hasOsType = YES;
+  result.osType = value;
+  return self;
+}
+- (EnvironmentBuilder*) clearOsType {
+  result.hasOsType = NO;
+  result.osType = EnvironmentOSUnknown;
+  return self;
+}
+- (BOOL) hasOsVersion {
+  return result.hasOsVersion;
+}
+- (NSString*) osVersion {
+  return result.osVersion;
+}
+- (EnvironmentBuilder*) setOsVersion:(NSString*) value {
+  result.hasOsVersion = YES;
+  result.osVersion = value;
+  return self;
+}
+- (EnvironmentBuilder*) clearOsVersion {
+  result.hasOsVersion = NO;
+  result.osVersion = @"";
+  return self;
+}
+- (BOOL) hasBuildModel {
+  return result.hasBuildModel;
+}
+- (NSString*) buildModel {
+  return result.buildModel;
+}
+- (EnvironmentBuilder*) setBuildModel:(NSString*) value {
+  result.hasBuildModel = YES;
+  result.buildModel = value;
+  return self;
+}
+- (EnvironmentBuilder*) clearBuildModel {
+  result.hasBuildModel = NO;
+  result.buildModel = @"";
+  return self;
+}
+- (BOOL) hasBuildManufacturer {
+  return result.hasBuildManufacturer;
+}
+- (NSString*) buildManufacturer {
+  return result.buildManufacturer;
+}
+- (EnvironmentBuilder*) setBuildManufacturer:(NSString*) value {
+  result.hasBuildManufacturer = YES;
+  result.buildManufacturer = value;
+  return self;
+}
+- (EnvironmentBuilder*) clearBuildManufacturer {
+  result.hasBuildManufacturer = NO;
+  result.buildManufacturer = @"";
+  return self;
+}
+- (BOOL) hasMobileCarrier {
+  return result.hasMobileCarrier;
+}
+- (NSString*) mobileCarrier {
+  return result.mobileCarrier;
+}
+- (EnvironmentBuilder*) setMobileCarrier:(NSString*) value {
+  result.hasMobileCarrier = YES;
+  result.mobileCarrier = value;
+  return self;
+}
+- (EnvironmentBuilder*) clearMobileCarrier {
+  result.hasMobileCarrier = NO;
+  result.mobileCarrier = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Event.pb.h b/src/gen_proto/Event.pb.h
new file mode 100644
index 0000000..e2261d6
--- /dev/null
+++ b/src/gen_proto/Event.pb.h
@@ -0,0 +1,118 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+#import "Pair.pb.h"
+#import "Weave_operation.pb.h"
+// @@protoc_insertion_point(imports)
+
+@class Event;
+@class EventBuilder;
+@class Pair;
+@class PairBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+
+@interface EventRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface Event : PBGeneratedMessage {
+@private
+  BOOL hasLogMessage_:1;
+  BOOL hasTimestampIso8601_:1;
+  BOOL hasOperation_:1;
+  BOOL hasTimestampMillis_:1;
+  NSString* logMessage;
+  NSString* timestampIso8601;
+  WeaveOperation operation;
+  SInt64 timestampMillis;
+  NSMutableArray * additionalDataArray;
+}
+- (BOOL) hasTimestampMillis;
+- (BOOL) hasLogMessage;
+- (BOOL) hasOperation;
+- (BOOL) hasTimestampIso8601;
+@property (readonly) SInt64 timestampMillis;
+@property (readonly, strong) NSString* logMessage;
+@property (readonly, strong) NSArray * additionalData;
+@property (readonly) WeaveOperation operation;
+@property (readonly, strong) NSString* timestampIso8601;
+- (Pair*)additionalDataAtIndex:(NSUInteger)index;
+
++ (Event*) defaultInstance;
+- (Event*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (EventBuilder*) builder;
++ (EventBuilder*) builder;
++ (EventBuilder*) builderWithPrototype:(Event*) prototype;
+- (EventBuilder*) toBuilder;
+
++ (Event*) parseFromData:(NSData*) data;
++ (Event*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Event*) parseFromInputStream:(NSInputStream*) input;
++ (Event*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Event*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Event*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface EventBuilder : PBGeneratedMessageBuilder {
+@private
+  Event* result;
+}
+
+- (Event*) defaultInstance;
+
+- (EventBuilder*) clear;
+- (EventBuilder*) clone;
+
+- (Event*) build;
+- (Event*) buildPartial;
+
+- (EventBuilder*) mergeFrom:(Event*) other;
+- (EventBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (EventBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasTimestampMillis;
+- (SInt64) timestampMillis;
+- (EventBuilder*) setTimestampMillis:(SInt64) value;
+- (EventBuilder*) clearTimestampMillis;
+
+- (BOOL) hasLogMessage;
+- (NSString*) logMessage;
+- (EventBuilder*) setLogMessage:(NSString*) value;
+- (EventBuilder*) clearLogMessage;
+
+- (NSMutableArray *)additionalData;
+- (Pair*)additionalDataAtIndex:(NSUInteger)index;
+- (EventBuilder *)addAdditionalData:(Pair*)value;
+- (EventBuilder *)setAdditionalDataArray:(NSArray *)array;
+- (EventBuilder *)clearAdditionalData;
+
+- (BOOL) hasOperation;
+- (WeaveOperation) operation;
+- (EventBuilder*) setOperation:(WeaveOperation) value;
+- (EventBuilder*) clearOperation;
+
+- (BOOL) hasTimestampIso8601;
+- (NSString*) timestampIso8601;
+- (EventBuilder*) setTimestampIso8601:(NSString*) value;
+- (EventBuilder*) clearTimestampIso8601;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Event.pb.m b/src/gen_proto/Event.pb.m
new file mode 100644
index 0000000..3b97e04
--- /dev/null
+++ b/src/gen_proto/Event.pb.m
@@ -0,0 +1,428 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Event.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation EventRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [EventRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    [PairRoot registerAllExtensions:registry];
+    [WeaveOperationRoot registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface Event ()
+@property SInt64 timestampMillis;
+@property (strong) NSString* logMessage;
+@property (strong) NSMutableArray * additionalDataArray;
+@property WeaveOperation operation;
+@property (strong) NSString* timestampIso8601;
+@end
+
+@implementation Event
+
+- (BOOL) hasTimestampMillis {
+  return !!hasTimestampMillis_;
+}
+- (void) setHasTimestampMillis:(BOOL) value_ {
+  hasTimestampMillis_ = !!value_;
+}
+@synthesize timestampMillis;
+- (BOOL) hasLogMessage {
+  return !!hasLogMessage_;
+}
+- (void) setHasLogMessage:(BOOL) value_ {
+  hasLogMessage_ = !!value_;
+}
+@synthesize logMessage;
+@synthesize additionalDataArray;
+@dynamic additionalData;
+- (BOOL) hasOperation {
+  return !!hasOperation_;
+}
+- (void) setHasOperation:(BOOL) value_ {
+  hasOperation_ = !!value_;
+}
+@synthesize operation;
+- (BOOL) hasTimestampIso8601 {
+  return !!hasTimestampIso8601_;
+}
+- (void) setHasTimestampIso8601:(BOOL) value_ {
+  hasTimestampIso8601_ = !!value_;
+}
+@synthesize timestampIso8601;
+- (id) init {
+  if ((self = [super init])) {
+    self.timestampMillis = 0L;
+    self.logMessage = @"";
+    self.operation = WeaveOperationNone;
+    self.timestampIso8601 = @"";
+  }
+  return self;
+}
+static Event* defaultEventInstance = nil;
++ (void) initialize {
+  if (self == [Event class]) {
+    defaultEventInstance = [[Event alloc] init];
+  }
+}
++ (Event*) defaultInstance {
+  return defaultEventInstance;
+}
+- (Event*) defaultInstance {
+  return defaultEventInstance;
+}
+- (NSArray *)additionalData {
+  return additionalDataArray;
+}
+- (Pair*)additionalDataAtIndex:(NSUInteger)index {
+  return [additionalDataArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasTimestampMillis) {
+    [output writeSInt64:1 value:self.timestampMillis];
+  }
+  if (self.hasLogMessage) {
+    [output writeString:2 value:self.logMessage];
+  }
+  [self.additionalDataArray enumerateObjectsUsingBlock:^(Pair *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:3 value:element];
+  }];
+  if (self.hasOperation) {
+    [output writeEnum:4 value:self.operation];
+  }
+  if (self.hasTimestampIso8601) {
+    [output writeString:5 value:self.timestampIso8601];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasTimestampMillis) {
+    size_ += computeSInt64Size(1, self.timestampMillis);
+  }
+  if (self.hasLogMessage) {
+    size_ += computeStringSize(2, self.logMessage);
+  }
+  [self.additionalDataArray enumerateObjectsUsingBlock:^(Pair *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(3, element);
+  }];
+  if (self.hasOperation) {
+    size_ += computeEnumSize(4, self.operation);
+  }
+  if (self.hasTimestampIso8601) {
+    size_ += computeStringSize(5, self.timestampIso8601);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Event*) parseFromData:(NSData*) data {
+  return (Event*)[[[Event builder] mergeFromData:data] build];
+}
++ (Event*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Event*)[[[Event builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Event*) parseFromInputStream:(NSInputStream*) input {
+  return (Event*)[[[Event builder] mergeFromInputStream:input] build];
+}
++ (Event*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Event*)[[[Event builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Event*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Event*)[[[Event builder] mergeFromCodedInputStream:input] build];
+}
++ (Event*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Event*)[[[Event builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (EventBuilder*) builder {
+  return [[EventBuilder alloc] init];
+}
++ (EventBuilder*) builderWithPrototype:(Event*) prototype {
+  return [[Event builder] mergeFrom:prototype];
+}
+- (EventBuilder*) builder {
+  return [Event builder];
+}
+- (EventBuilder*) toBuilder {
+  return [Event builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasTimestampMillis) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"timestampMillis", [NSNumber numberWithLongLong:self.timestampMillis]];
+  }
+  if (self.hasLogMessage) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"logMessage", self.logMessage];
+  }
+  [self.additionalDataArray enumerateObjectsUsingBlock:^(Pair *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"additionalData"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasOperation) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"operation", self.operation];
+  }
+  if (self.hasTimestampIso8601) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"timestampIso8601", self.timestampIso8601];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Event class]]) {
+    return NO;
+  }
+  Event *otherMessage = other;
+  return
+      self.hasTimestampMillis == otherMessage.hasTimestampMillis &&
+      (!self.hasTimestampMillis || self.timestampMillis == otherMessage.timestampMillis) &&
+      self.hasLogMessage == otherMessage.hasLogMessage &&
+      (!self.hasLogMessage || [self.logMessage isEqual:otherMessage.logMessage]) &&
+      [self.additionalDataArray isEqualToArray:otherMessage.additionalDataArray] &&
+      self.hasOperation == otherMessage.hasOperation &&
+      (!self.hasOperation || self.operation == otherMessage.operation) &&
+      self.hasTimestampIso8601 == otherMessage.hasTimestampIso8601 &&
+      (!self.hasTimestampIso8601 || [self.timestampIso8601 isEqual:otherMessage.timestampIso8601]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasTimestampMillis) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.timestampMillis] hash];
+  }
+  if (self.hasLogMessage) {
+    hashCode = hashCode * 31 + [self.logMessage hash];
+  }
+  [self.additionalDataArray enumerateObjectsUsingBlock:^(Pair *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasOperation) {
+    hashCode = hashCode * 31 + self.operation;
+  }
+  if (self.hasTimestampIso8601) {
+    hashCode = hashCode * 31 + [self.timestampIso8601 hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface EventBuilder()
+@property (strong) Event* result;
+@end
+
+@implementation EventBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Event alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (EventBuilder*) clear {
+  self.result = [[Event alloc] init];
+  return self;
+}
+- (EventBuilder*) clone {
+  return [Event builderWithPrototype:result];
+}
+- (Event*) defaultInstance {
+  return [Event defaultInstance];
+}
+- (Event*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Event*) buildPartial {
+  Event* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (EventBuilder*) mergeFrom:(Event*) other {
+  if (other == [Event defaultInstance]) {
+    return self;
+  }
+  if (other.hasTimestampMillis) {
+    [self setTimestampMillis:other.timestampMillis];
+  }
+  if (other.hasLogMessage) {
+    [self setLogMessage:other.logMessage];
+  }
+  if (other.additionalDataArray.count > 0) {
+    if (result.additionalDataArray == nil) {
+      result.additionalDataArray = [[NSMutableArray alloc] initWithArray:other.additionalDataArray];
+    } else {
+      [result.additionalDataArray addObjectsFromArray:other.additionalDataArray];
+    }
+  }
+  if (other.hasOperation) {
+    [self setOperation:other.operation];
+  }
+  if (other.hasTimestampIso8601) {
+    [self setTimestampIso8601:other.timestampIso8601];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (EventBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (EventBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setTimestampMillis:[input readSInt64]];
+        break;
+      }
+      case 18: {
+        [self setLogMessage:[input readString]];
+        break;
+      }
+      case 26: {
+        PairBuilder* subBuilder = [Pair builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addAdditionalData:[subBuilder buildPartial]];
+        break;
+      }
+      case 32: {
+        WeaveOperation value = (WeaveOperation)[input readEnum];
+        if (WeaveOperationIsValidValue(value)) {
+          [self setOperation:value];
+        } else {
+          [unknownFields mergeVarintField:4 value:value];
+        }
+        break;
+      }
+      case 42: {
+        [self setTimestampIso8601:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasTimestampMillis {
+  return result.hasTimestampMillis;
+}
+- (SInt64) timestampMillis {
+  return result.timestampMillis;
+}
+- (EventBuilder*) setTimestampMillis:(SInt64) value {
+  result.hasTimestampMillis = YES;
+  result.timestampMillis = value;
+  return self;
+}
+- (EventBuilder*) clearTimestampMillis {
+  result.hasTimestampMillis = NO;
+  result.timestampMillis = 0L;
+  return self;
+}
+- (BOOL) hasLogMessage {
+  return result.hasLogMessage;
+}
+- (NSString*) logMessage {
+  return result.logMessage;
+}
+- (EventBuilder*) setLogMessage:(NSString*) value {
+  result.hasLogMessage = YES;
+  result.logMessage = value;
+  return self;
+}
+- (EventBuilder*) clearLogMessage {
+  result.hasLogMessage = NO;
+  result.logMessage = @"";
+  return self;
+}
+- (NSMutableArray *)additionalData {
+  return result.additionalDataArray;
+}
+- (Pair*)additionalDataAtIndex:(NSUInteger)index {
+  return [result additionalDataAtIndex:index];
+}
+- (EventBuilder *)addAdditionalData:(Pair*)value {
+  if (result.additionalDataArray == nil) {
+    result.additionalDataArray = [[NSMutableArray alloc]init];
+  }
+  [result.additionalDataArray addObject:value];
+  return self;
+}
+- (EventBuilder *)setAdditionalDataArray:(NSArray *)array {
+  result.additionalDataArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (EventBuilder *)clearAdditionalData {
+  result.additionalDataArray = nil;
+  return self;
+}
+- (BOOL) hasOperation {
+  return result.hasOperation;
+}
+- (WeaveOperation) operation {
+  return result.operation;
+}
+- (EventBuilder*) setOperation:(WeaveOperation) value {
+  result.hasOperation = YES;
+  result.operation = value;
+  return self;
+}
+- (EventBuilder*) clearOperation {
+  result.hasOperation = NO;
+  result.operation = WeaveOperationNone;
+  return self;
+}
+- (BOOL) hasTimestampIso8601 {
+  return result.hasTimestampIso8601;
+}
+- (NSString*) timestampIso8601 {
+  return result.timestampIso8601;
+}
+- (EventBuilder*) setTimestampIso8601:(NSString*) value {
+  result.hasTimestampIso8601 = YES;
+  result.timestampIso8601 = value;
+  return self;
+}
+- (EventBuilder*) clearTimestampIso8601 {
+  result.hasTimestampIso8601 = NO;
+  result.timestampIso8601 = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Fabric_info.pb.h b/src/gen_proto/Fabric_info.pb.h
new file mode 100644
index 0000000..b116acf
--- /dev/null
+++ b/src/gen_proto/Fabric_info.pb.h
@@ -0,0 +1,87 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class FabricInfo;
+@class FabricInfoBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+
+@interface FabricInfoRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface FabricInfo : PBGeneratedMessage {
+@private
+  BOOL hasPrimaryFabricId_:1;
+  NSString* primaryFabricId;
+  NSMutableArray * assistingDeviceIdsArray;
+}
+- (BOOL) hasPrimaryFabricId;
+@property (readonly, strong) NSString* primaryFabricId;
+@property (readonly, strong) PBArray * assistingDeviceIds;
+- (NSString*)assistingDeviceIdsAtIndex:(NSUInteger)index;
+
++ (FabricInfo*) defaultInstance;
+- (FabricInfo*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (FabricInfoBuilder*) builder;
++ (FabricInfoBuilder*) builder;
++ (FabricInfoBuilder*) builderWithPrototype:(FabricInfo*) prototype;
+- (FabricInfoBuilder*) toBuilder;
+
++ (FabricInfo*) parseFromData:(NSData*) data;
++ (FabricInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (FabricInfo*) parseFromInputStream:(NSInputStream*) input;
++ (FabricInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (FabricInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (FabricInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface FabricInfoBuilder : PBGeneratedMessageBuilder {
+@private
+  FabricInfo* result;
+}
+
+- (FabricInfo*) defaultInstance;
+
+- (FabricInfoBuilder*) clear;
+- (FabricInfoBuilder*) clone;
+
+- (FabricInfo*) build;
+- (FabricInfo*) buildPartial;
+
+- (FabricInfoBuilder*) mergeFrom:(FabricInfo*) other;
+- (FabricInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (FabricInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasPrimaryFabricId;
+- (NSString*) primaryFabricId;
+- (FabricInfoBuilder*) setPrimaryFabricId:(NSString*) value;
+- (FabricInfoBuilder*) clearPrimaryFabricId;
+
+- (NSMutableArray *)assistingDeviceIds;
+- (NSString*)assistingDeviceIdsAtIndex:(NSUInteger)index;
+- (FabricInfoBuilder *)addAssistingDeviceIds:(NSString*)value;
+- (FabricInfoBuilder *)setAssistingDeviceIdsArray:(NSArray *)array;
+- (FabricInfoBuilder *)clearAssistingDeviceIds;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Fabric_info.pb.m b/src/gen_proto/Fabric_info.pb.m
new file mode 100644
index 0000000..7d8fe12
--- /dev/null
+++ b/src/gen_proto/Fabric_info.pb.m
@@ -0,0 +1,284 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Fabric_info.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation FabricInfoRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [FabricInfoRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface FabricInfo ()
+@property (strong) NSString* primaryFabricId;
+@property (strong) NSMutableArray * assistingDeviceIdsArray;
+@end
+
+@implementation FabricInfo
+
+- (BOOL) hasPrimaryFabricId {
+  return !!hasPrimaryFabricId_;
+}
+- (void) setHasPrimaryFabricId:(BOOL) value_ {
+  hasPrimaryFabricId_ = !!value_;
+}
+@synthesize primaryFabricId;
+@synthesize assistingDeviceIdsArray;
+@dynamic assistingDeviceIds;
+- (id) init {
+  if ((self = [super init])) {
+    self.primaryFabricId = @"";
+  }
+  return self;
+}
+static FabricInfo* defaultFabricInfoInstance = nil;
++ (void) initialize {
+  if (self == [FabricInfo class]) {
+    defaultFabricInfoInstance = [[FabricInfo alloc] init];
+  }
+}
++ (FabricInfo*) defaultInstance {
+  return defaultFabricInfoInstance;
+}
+- (FabricInfo*) defaultInstance {
+  return defaultFabricInfoInstance;
+}
+- (NSArray *)assistingDeviceIds {
+  return assistingDeviceIdsArray;
+}
+- (NSString*)assistingDeviceIdsAtIndex:(NSUInteger)index {
+  return [assistingDeviceIdsArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasPrimaryFabricId) {
+    [output writeString:1 value:self.primaryFabricId];
+  }
+  [self.assistingDeviceIdsArray enumerateObjectsUsingBlock:^(NSString *element, NSUInteger idx, BOOL *stop) {
+    [output writeString:2 value:element];
+  }];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasPrimaryFabricId) {
+    size_ += computeStringSize(1, self.primaryFabricId);
+  }
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.assistingDeviceIdsArray.count;
+    [self.assistingDeviceIdsArray enumerateObjectsUsingBlock:^(NSString *element, NSUInteger idx, BOOL *stop) {
+      dataSize += computeStringSizeNoTag(element);
+    }];
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (FabricInfo*) parseFromData:(NSData*) data {
+  return (FabricInfo*)[[[FabricInfo builder] mergeFromData:data] build];
+}
++ (FabricInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (FabricInfo*)[[[FabricInfo builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (FabricInfo*) parseFromInputStream:(NSInputStream*) input {
+  return (FabricInfo*)[[[FabricInfo builder] mergeFromInputStream:input] build];
+}
++ (FabricInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (FabricInfo*)[[[FabricInfo builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (FabricInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (FabricInfo*)[[[FabricInfo builder] mergeFromCodedInputStream:input] build];
+}
++ (FabricInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (FabricInfo*)[[[FabricInfo builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (FabricInfoBuilder*) builder {
+  return [[FabricInfoBuilder alloc] init];
+}
++ (FabricInfoBuilder*) builderWithPrototype:(FabricInfo*) prototype {
+  return [[FabricInfo builder] mergeFrom:prototype];
+}
+- (FabricInfoBuilder*) builder {
+  return [FabricInfo builder];
+}
+- (FabricInfoBuilder*) toBuilder {
+  return [FabricInfo builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasPrimaryFabricId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"primaryFabricId", self.primaryFabricId];
+  }
+  [self.assistingDeviceIdsArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"assistingDeviceIds", obj];
+  }];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[FabricInfo class]]) {
+    return NO;
+  }
+  FabricInfo *otherMessage = other;
+  return
+      self.hasPrimaryFabricId == otherMessage.hasPrimaryFabricId &&
+      (!self.hasPrimaryFabricId || [self.primaryFabricId isEqual:otherMessage.primaryFabricId]) &&
+      [self.assistingDeviceIdsArray isEqualToArray:otherMessage.assistingDeviceIdsArray] &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasPrimaryFabricId) {
+    hashCode = hashCode * 31 + [self.primaryFabricId hash];
+  }
+  [self.assistingDeviceIdsArray enumerateObjectsUsingBlock:^(id element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface FabricInfoBuilder()
+@property (strong) FabricInfo* result;
+@end
+
+@implementation FabricInfoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[FabricInfo alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (FabricInfoBuilder*) clear {
+  self.result = [[FabricInfo alloc] init];
+  return self;
+}
+- (FabricInfoBuilder*) clone {
+  return [FabricInfo builderWithPrototype:result];
+}
+- (FabricInfo*) defaultInstance {
+  return [FabricInfo defaultInstance];
+}
+- (FabricInfo*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (FabricInfo*) buildPartial {
+  FabricInfo* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (FabricInfoBuilder*) mergeFrom:(FabricInfo*) other {
+  if (other == [FabricInfo defaultInstance]) {
+    return self;
+  }
+  if (other.hasPrimaryFabricId) {
+    [self setPrimaryFabricId:other.primaryFabricId];
+  }
+  if (other.assistingDeviceIdsArray.count > 0) {
+    if (result.assistingDeviceIdsArray == nil) {
+      result.assistingDeviceIdsArray = [[NSMutableArray alloc] initWithArray:other.assistingDeviceIdsArray];
+    } else {
+      [result.assistingDeviceIdsArray addObjectsFromArray:other.assistingDeviceIdsArray];
+    }
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (FabricInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (FabricInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setPrimaryFabricId:[input readString]];
+        break;
+      }
+      case 18: {
+        [self addAssistingDeviceIds:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasPrimaryFabricId {
+  return result.hasPrimaryFabricId;
+}
+- (NSString*) primaryFabricId {
+  return result.primaryFabricId;
+}
+- (FabricInfoBuilder*) setPrimaryFabricId:(NSString*) value {
+  result.hasPrimaryFabricId = YES;
+  result.primaryFabricId = value;
+  return self;
+}
+- (FabricInfoBuilder*) clearPrimaryFabricId {
+  result.hasPrimaryFabricId = NO;
+  result.primaryFabricId = @"";
+  return self;
+}
+- (NSMutableArray *)assistingDeviceIds {
+  return result.assistingDeviceIdsArray;
+}
+- (NSString*)assistingDeviceIdsAtIndex:(NSUInteger)index {
+  return [result assistingDeviceIdsAtIndex:index];
+}
+- (FabricInfoBuilder *)addAssistingDeviceIds:(NSString*)value {
+  if (result.assistingDeviceIdsArray == nil) {
+    result.assistingDeviceIdsArray = [[NSMutableArray alloc]init];
+  }
+  [result.assistingDeviceIdsArray addObject:value];
+  return self;
+}
+- (FabricInfoBuilder *)setAssistingDeviceIdsArray:(NSArray *)array {
+  result.assistingDeviceIdsArray = [[NSMutableArray alloc] initWithArray:array];
+  return self;
+}
+- (FabricInfoBuilder *)clearAssistingDeviceIds {
+  result.assistingDeviceIdsArray = nil;
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Identification_profile.pb.h b/src/gen_proto/Identification_profile.pb.h
new file mode 100644
index 0000000..f525c96
--- /dev/null
+++ b/src/gen_proto/Identification_profile.pb.h
@@ -0,0 +1,141 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class IdentificationProfile;
+@class IdentificationProfileBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+
+@interface IdentificationProfileRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface IdentificationProfile : PBGeneratedMessage {
+@private
+  BOOL hasNodeIdentifier_:1;
+  BOOL hasDeviceId_:1;
+  BOOL hasSerialNumber_:1;
+  BOOL hasVendorDescription_:1;
+  BOOL hasProductDescription_:1;
+  BOOL hasRevision_:1;
+  BOOL hasVendorId_:1;
+  BOOL hasProductId_:1;
+  UInt64 nodeIdentifier;
+  NSString* deviceId;
+  NSString* serialNumber;
+  NSString* vendorDescription;
+  NSString* productDescription;
+  NSString* revision;
+  UInt32 vendorId;
+  UInt32 productId;
+}
+- (BOOL) hasDeviceId;
+- (BOOL) hasNodeIdentifier;
+- (BOOL) hasSerialNumber;
+- (BOOL) hasVendorId;
+- (BOOL) hasVendorDescription;
+- (BOOL) hasProductId;
+- (BOOL) hasProductDescription;
+- (BOOL) hasRevision;
+@property (readonly, strong) NSString* deviceId;
+@property (readonly) UInt64 nodeIdentifier;
+@property (readonly, strong) NSString* serialNumber;
+@property (readonly) UInt32 vendorId;
+@property (readonly, strong) NSString* vendorDescription;
+@property (readonly) UInt32 productId;
+@property (readonly, strong) NSString* productDescription;
+@property (readonly, strong) NSString* revision;
+
++ (IdentificationProfile*) defaultInstance;
+- (IdentificationProfile*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (IdentificationProfileBuilder*) builder;
++ (IdentificationProfileBuilder*) builder;
++ (IdentificationProfileBuilder*) builderWithPrototype:(IdentificationProfile*) prototype;
+- (IdentificationProfileBuilder*) toBuilder;
+
++ (IdentificationProfile*) parseFromData:(NSData*) data;
++ (IdentificationProfile*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (IdentificationProfile*) parseFromInputStream:(NSInputStream*) input;
++ (IdentificationProfile*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (IdentificationProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (IdentificationProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface IdentificationProfileBuilder : PBGeneratedMessageBuilder {
+@private
+  IdentificationProfile* result;
+}
+
+- (IdentificationProfile*) defaultInstance;
+
+- (IdentificationProfileBuilder*) clear;
+- (IdentificationProfileBuilder*) clone;
+
+- (IdentificationProfile*) build;
+- (IdentificationProfile*) buildPartial;
+
+- (IdentificationProfileBuilder*) mergeFrom:(IdentificationProfile*) other;
+- (IdentificationProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (IdentificationProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasDeviceId;
+- (NSString*) deviceId;
+- (IdentificationProfileBuilder*) setDeviceId:(NSString*) value;
+- (IdentificationProfileBuilder*) clearDeviceId;
+
+- (BOOL) hasNodeIdentifier;
+- (UInt64) nodeIdentifier;
+- (IdentificationProfileBuilder*) setNodeIdentifier:(UInt64) value;
+- (IdentificationProfileBuilder*) clearNodeIdentifier;
+
+- (BOOL) hasSerialNumber;
+- (NSString*) serialNumber;
+- (IdentificationProfileBuilder*) setSerialNumber:(NSString*) value;
+- (IdentificationProfileBuilder*) clearSerialNumber;
+
+- (BOOL) hasVendorId;
+- (UInt32) vendorId;
+- (IdentificationProfileBuilder*) setVendorId:(UInt32) value;
+- (IdentificationProfileBuilder*) clearVendorId;
+
+- (BOOL) hasVendorDescription;
+- (NSString*) vendorDescription;
+- (IdentificationProfileBuilder*) setVendorDescription:(NSString*) value;
+- (IdentificationProfileBuilder*) clearVendorDescription;
+
+- (BOOL) hasProductId;
+- (UInt32) productId;
+- (IdentificationProfileBuilder*) setProductId:(UInt32) value;
+- (IdentificationProfileBuilder*) clearProductId;
+
+- (BOOL) hasProductDescription;
+- (NSString*) productDescription;
+- (IdentificationProfileBuilder*) setProductDescription:(NSString*) value;
+- (IdentificationProfileBuilder*) clearProductDescription;
+
+- (BOOL) hasRevision;
+- (NSString*) revision;
+- (IdentificationProfileBuilder*) setRevision:(NSString*) value;
+- (IdentificationProfileBuilder*) clearRevision;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Identification_profile.pb.m b/src/gen_proto/Identification_profile.pb.m
new file mode 100644
index 0000000..540bf59
--- /dev/null
+++ b/src/gen_proto/Identification_profile.pb.m
@@ -0,0 +1,546 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Identification_profile.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation IdentificationProfileRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [IdentificationProfileRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface IdentificationProfile ()
+@property (strong) NSString* deviceId;
+@property UInt64 nodeIdentifier;
+@property (strong) NSString* serialNumber;
+@property UInt32 vendorId;
+@property (strong) NSString* vendorDescription;
+@property UInt32 productId;
+@property (strong) NSString* productDescription;
+@property (strong) NSString* revision;
+@end
+
+@implementation IdentificationProfile
+
+- (BOOL) hasDeviceId {
+  return !!hasDeviceId_;
+}
+- (void) setHasDeviceId:(BOOL) value_ {
+  hasDeviceId_ = !!value_;
+}
+@synthesize deviceId;
+- (BOOL) hasNodeIdentifier {
+  return !!hasNodeIdentifier_;
+}
+- (void) setHasNodeIdentifier:(BOOL) value_ {
+  hasNodeIdentifier_ = !!value_;
+}
+@synthesize nodeIdentifier;
+- (BOOL) hasSerialNumber {
+  return !!hasSerialNumber_;
+}
+- (void) setHasSerialNumber:(BOOL) value_ {
+  hasSerialNumber_ = !!value_;
+}
+@synthesize serialNumber;
+- (BOOL) hasVendorId {
+  return !!hasVendorId_;
+}
+- (void) setHasVendorId:(BOOL) value_ {
+  hasVendorId_ = !!value_;
+}
+@synthesize vendorId;
+- (BOOL) hasVendorDescription {
+  return !!hasVendorDescription_;
+}
+- (void) setHasVendorDescription:(BOOL) value_ {
+  hasVendorDescription_ = !!value_;
+}
+@synthesize vendorDescription;
+- (BOOL) hasProductId {
+  return !!hasProductId_;
+}
+- (void) setHasProductId:(BOOL) value_ {
+  hasProductId_ = !!value_;
+}
+@synthesize productId;
+- (BOOL) hasProductDescription {
+  return !!hasProductDescription_;
+}
+- (void) setHasProductDescription:(BOOL) value_ {
+  hasProductDescription_ = !!value_;
+}
+@synthesize productDescription;
+- (BOOL) hasRevision {
+  return !!hasRevision_;
+}
+- (void) setHasRevision:(BOOL) value_ {
+  hasRevision_ = !!value_;
+}
+@synthesize revision;
+- (id) init {
+  if ((self = [super init])) {
+    self.deviceId = @"";
+    self.nodeIdentifier = 0L;
+    self.serialNumber = @"";
+    self.vendorId = 0;
+    self.vendorDescription = @"";
+    self.productId = 0;
+    self.productDescription = @"";
+    self.revision = @"";
+  }
+  return self;
+}
+static IdentificationProfile* defaultIdentificationProfileInstance = nil;
++ (void) initialize {
+  if (self == [IdentificationProfile class]) {
+    defaultIdentificationProfileInstance = [[IdentificationProfile alloc] init];
+  }
+}
++ (IdentificationProfile*) defaultInstance {
+  return defaultIdentificationProfileInstance;
+}
+- (IdentificationProfile*) defaultInstance {
+  return defaultIdentificationProfileInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasDeviceId) {
+    [output writeString:1 value:self.deviceId];
+  }
+  if (self.hasNodeIdentifier) {
+    [output writeUInt64:2 value:self.nodeIdentifier];
+  }
+  if (self.hasSerialNumber) {
+    [output writeString:3 value:self.serialNumber];
+  }
+  if (self.hasVendorId) {
+    [output writeUInt32:4 value:self.vendorId];
+  }
+  if (self.hasVendorDescription) {
+    [output writeString:5 value:self.vendorDescription];
+  }
+  if (self.hasProductId) {
+    [output writeUInt32:6 value:self.productId];
+  }
+  if (self.hasProductDescription) {
+    [output writeString:7 value:self.productDescription];
+  }
+  if (self.hasRevision) {
+    [output writeString:8 value:self.revision];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasDeviceId) {
+    size_ += computeStringSize(1, self.deviceId);
+  }
+  if (self.hasNodeIdentifier) {
+    size_ += computeUInt64Size(2, self.nodeIdentifier);
+  }
+  if (self.hasSerialNumber) {
+    size_ += computeStringSize(3, self.serialNumber);
+  }
+  if (self.hasVendorId) {
+    size_ += computeUInt32Size(4, self.vendorId);
+  }
+  if (self.hasVendorDescription) {
+    size_ += computeStringSize(5, self.vendorDescription);
+  }
+  if (self.hasProductId) {
+    size_ += computeUInt32Size(6, self.productId);
+  }
+  if (self.hasProductDescription) {
+    size_ += computeStringSize(7, self.productDescription);
+  }
+  if (self.hasRevision) {
+    size_ += computeStringSize(8, self.revision);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (IdentificationProfile*) parseFromData:(NSData*) data {
+  return (IdentificationProfile*)[[[IdentificationProfile builder] mergeFromData:data] build];
+}
++ (IdentificationProfile*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (IdentificationProfile*)[[[IdentificationProfile builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (IdentificationProfile*) parseFromInputStream:(NSInputStream*) input {
+  return (IdentificationProfile*)[[[IdentificationProfile builder] mergeFromInputStream:input] build];
+}
++ (IdentificationProfile*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (IdentificationProfile*)[[[IdentificationProfile builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (IdentificationProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (IdentificationProfile*)[[[IdentificationProfile builder] mergeFromCodedInputStream:input] build];
+}
++ (IdentificationProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (IdentificationProfile*)[[[IdentificationProfile builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (IdentificationProfileBuilder*) builder {
+  return [[IdentificationProfileBuilder alloc] init];
+}
++ (IdentificationProfileBuilder*) builderWithPrototype:(IdentificationProfile*) prototype {
+  return [[IdentificationProfile builder] mergeFrom:prototype];
+}
+- (IdentificationProfileBuilder*) builder {
+  return [IdentificationProfile builder];
+}
+- (IdentificationProfileBuilder*) toBuilder {
+  return [IdentificationProfile builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasDeviceId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deviceId", self.deviceId];
+  }
+  if (self.hasNodeIdentifier) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"nodeIdentifier", [NSNumber numberWithLongLong:self.nodeIdentifier]];
+  }
+  if (self.hasSerialNumber) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"serialNumber", self.serialNumber];
+  }
+  if (self.hasVendorId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"vendorId", [NSNumber numberWithInteger:self.vendorId]];
+  }
+  if (self.hasVendorDescription) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"vendorDescription", self.vendorDescription];
+  }
+  if (self.hasProductId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"productId", [NSNumber numberWithInteger:self.productId]];
+  }
+  if (self.hasProductDescription) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"productDescription", self.productDescription];
+  }
+  if (self.hasRevision) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"revision", self.revision];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[IdentificationProfile class]]) {
+    return NO;
+  }
+  IdentificationProfile *otherMessage = other;
+  return
+      self.hasDeviceId == otherMessage.hasDeviceId &&
+      (!self.hasDeviceId || [self.deviceId isEqual:otherMessage.deviceId]) &&
+      self.hasNodeIdentifier == otherMessage.hasNodeIdentifier &&
+      (!self.hasNodeIdentifier || self.nodeIdentifier == otherMessage.nodeIdentifier) &&
+      self.hasSerialNumber == otherMessage.hasSerialNumber &&
+      (!self.hasSerialNumber || [self.serialNumber isEqual:otherMessage.serialNumber]) &&
+      self.hasVendorId == otherMessage.hasVendorId &&
+      (!self.hasVendorId || self.vendorId == otherMessage.vendorId) &&
+      self.hasVendorDescription == otherMessage.hasVendorDescription &&
+      (!self.hasVendorDescription || [self.vendorDescription isEqual:otherMessage.vendorDescription]) &&
+      self.hasProductId == otherMessage.hasProductId &&
+      (!self.hasProductId || self.productId == otherMessage.productId) &&
+      self.hasProductDescription == otherMessage.hasProductDescription &&
+      (!self.hasProductDescription || [self.productDescription isEqual:otherMessage.productDescription]) &&
+      self.hasRevision == otherMessage.hasRevision &&
+      (!self.hasRevision || [self.revision isEqual:otherMessage.revision]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasDeviceId) {
+    hashCode = hashCode * 31 + [self.deviceId hash];
+  }
+  if (self.hasNodeIdentifier) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.nodeIdentifier] hash];
+  }
+  if (self.hasSerialNumber) {
+    hashCode = hashCode * 31 + [self.serialNumber hash];
+  }
+  if (self.hasVendorId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.vendorId] hash];
+  }
+  if (self.hasVendorDescription) {
+    hashCode = hashCode * 31 + [self.vendorDescription hash];
+  }
+  if (self.hasProductId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.productId] hash];
+  }
+  if (self.hasProductDescription) {
+    hashCode = hashCode * 31 + [self.productDescription hash];
+  }
+  if (self.hasRevision) {
+    hashCode = hashCode * 31 + [self.revision hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface IdentificationProfileBuilder()
+@property (strong) IdentificationProfile* result;
+@end
+
+@implementation IdentificationProfileBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[IdentificationProfile alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (IdentificationProfileBuilder*) clear {
+  self.result = [[IdentificationProfile alloc] init];
+  return self;
+}
+- (IdentificationProfileBuilder*) clone {
+  return [IdentificationProfile builderWithPrototype:result];
+}
+- (IdentificationProfile*) defaultInstance {
+  return [IdentificationProfile defaultInstance];
+}
+- (IdentificationProfile*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (IdentificationProfile*) buildPartial {
+  IdentificationProfile* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (IdentificationProfileBuilder*) mergeFrom:(IdentificationProfile*) other {
+  if (other == [IdentificationProfile defaultInstance]) {
+    return self;
+  }
+  if (other.hasDeviceId) {
+    [self setDeviceId:other.deviceId];
+  }
+  if (other.hasNodeIdentifier) {
+    [self setNodeIdentifier:other.nodeIdentifier];
+  }
+  if (other.hasSerialNumber) {
+    [self setSerialNumber:other.serialNumber];
+  }
+  if (other.hasVendorId) {
+    [self setVendorId:other.vendorId];
+  }
+  if (other.hasVendorDescription) {
+    [self setVendorDescription:other.vendorDescription];
+  }
+  if (other.hasProductId) {
+    [self setProductId:other.productId];
+  }
+  if (other.hasProductDescription) {
+    [self setProductDescription:other.productDescription];
+  }
+  if (other.hasRevision) {
+    [self setRevision:other.revision];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (IdentificationProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (IdentificationProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setDeviceId:[input readString]];
+        break;
+      }
+      case 16: {
+        [self setNodeIdentifier:[input readUInt64]];
+        break;
+      }
+      case 26: {
+        [self setSerialNumber:[input readString]];
+        break;
+      }
+      case 32: {
+        [self setVendorId:[input readUInt32]];
+        break;
+      }
+      case 42: {
+        [self setVendorDescription:[input readString]];
+        break;
+      }
+      case 48: {
+        [self setProductId:[input readUInt32]];
+        break;
+      }
+      case 58: {
+        [self setProductDescription:[input readString]];
+        break;
+      }
+      case 66: {
+        [self setRevision:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasDeviceId {
+  return result.hasDeviceId;
+}
+- (NSString*) deviceId {
+  return result.deviceId;
+}
+- (IdentificationProfileBuilder*) setDeviceId:(NSString*) value {
+  result.hasDeviceId = YES;
+  result.deviceId = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearDeviceId {
+  result.hasDeviceId = NO;
+  result.deviceId = @"";
+  return self;
+}
+- (BOOL) hasNodeIdentifier {
+  return result.hasNodeIdentifier;
+}
+- (UInt64) nodeIdentifier {
+  return result.nodeIdentifier;
+}
+- (IdentificationProfileBuilder*) setNodeIdentifier:(UInt64) value {
+  result.hasNodeIdentifier = YES;
+  result.nodeIdentifier = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearNodeIdentifier {
+  result.hasNodeIdentifier = NO;
+  result.nodeIdentifier = 0L;
+  return self;
+}
+- (BOOL) hasSerialNumber {
+  return result.hasSerialNumber;
+}
+- (NSString*) serialNumber {
+  return result.serialNumber;
+}
+- (IdentificationProfileBuilder*) setSerialNumber:(NSString*) value {
+  result.hasSerialNumber = YES;
+  result.serialNumber = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearSerialNumber {
+  result.hasSerialNumber = NO;
+  result.serialNumber = @"";
+  return self;
+}
+- (BOOL) hasVendorId {
+  return result.hasVendorId;
+}
+- (UInt32) vendorId {
+  return result.vendorId;
+}
+- (IdentificationProfileBuilder*) setVendorId:(UInt32) value {
+  result.hasVendorId = YES;
+  result.vendorId = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearVendorId {
+  result.hasVendorId = NO;
+  result.vendorId = 0;
+  return self;
+}
+- (BOOL) hasVendorDescription {
+  return result.hasVendorDescription;
+}
+- (NSString*) vendorDescription {
+  return result.vendorDescription;
+}
+- (IdentificationProfileBuilder*) setVendorDescription:(NSString*) value {
+  result.hasVendorDescription = YES;
+  result.vendorDescription = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearVendorDescription {
+  result.hasVendorDescription = NO;
+  result.vendorDescription = @"";
+  return self;
+}
+- (BOOL) hasProductId {
+  return result.hasProductId;
+}
+- (UInt32) productId {
+  return result.productId;
+}
+- (IdentificationProfileBuilder*) setProductId:(UInt32) value {
+  result.hasProductId = YES;
+  result.productId = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearProductId {
+  result.hasProductId = NO;
+  result.productId = 0;
+  return self;
+}
+- (BOOL) hasProductDescription {
+  return result.hasProductDescription;
+}
+- (NSString*) productDescription {
+  return result.productDescription;
+}
+- (IdentificationProfileBuilder*) setProductDescription:(NSString*) value {
+  result.hasProductDescription = YES;
+  result.productDescription = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearProductDescription {
+  result.hasProductDescription = NO;
+  result.productDescription = @"";
+  return self;
+}
+- (BOOL) hasRevision {
+  return result.hasRevision;
+}
+- (NSString*) revision {
+  return result.revision;
+}
+- (IdentificationProfileBuilder*) setRevision:(NSString*) value {
+  result.hasRevision = YES;
+  result.revision = value;
+  return self;
+}
+- (IdentificationProfileBuilder*) clearRevision {
+  result.hasRevision = NO;
+  result.revision = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Nexustalk.pb.h b/src/gen_proto/Nexustalk.pb.h
new file mode 100644
index 0000000..947328c
--- /dev/null
+++ b/src/gen_proto/Nexustalk.pb.h
@@ -0,0 +1,1260 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+#import "Commontalk.pb.h"
+// @@protoc_insertion_point(imports)
+
+@class AudioPayload;
+@class AudioPayloadBuilder;
+@class ClockSync;
+@class ClockSyncBuilder;
+@class ClockSyncEcho;
+@class ClockSyncEchoBuilder;
+@class Error;
+@class ErrorBuilder;
+@class Hello;
+@class HelloBuilder;
+@class LatencyMeasure;
+@class LatencyMeasureBuilder;
+@class Ok;
+@class OkBuilder;
+@class Ping;
+@class PingBuilder;
+@class PingCamera;
+@class PingCameraBuilder;
+@class PlaybackBegin;
+@class PlaybackBeginBuilder;
+@class PlaybackBeginStream;
+@class PlaybackBeginStreamBuilder;
+@class PlaybackEnd;
+@class PlaybackEndBuilder;
+@class PlaybackPacket;
+@class PlaybackPacketBuilder;
+@class Redirect;
+@class RedirectBuilder;
+@class StartPlayback;
+@class StartPlaybackBuilder;
+@class StopPlayback;
+@class StopPlaybackBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  PacketTypePacketTypePing = 1,
+  PacketTypePacketTypeHello = 100,
+  PacketTypePacketTypePingCamera = 101,
+  PacketTypePacketTypeAudioPayload = 102,
+  PacketTypePacketTypeStartPlayback = 103,
+  PacketTypePacketTypeStopPlayback = 104,
+  PacketTypePacketTypeClockSyncEcho = 105,
+  PacketTypePacketTypeLatencyMeasure = 106,
+  PacketTypePacketTypeOk = 200,
+  PacketTypePacketTypeError = 201,
+  PacketTypePacketTypePlaybackBegin = 202,
+  PacketTypePacketTypePlaybackEnd = 203,
+  PacketTypePacketTypePlaybackPacket = 204,
+  PacketTypePacketTypeLongPlaybackPacket = 205,
+  PacketTypePacketTypeClockSync = 206,
+  PacketTypePacketTypeRedirect = 207,
+} PacketType;
+
+BOOL PacketTypeIsValidValue(PacketType value);
+
+typedef enum {
+  ErrorCodeErrorCameraNotConnected = 1,
+  ErrorCodeErrorIllegalPacket = 2,
+  ErrorCodeErrorAuthorizationFailed = 3,
+  ErrorCodeErrorNoTranscoderAvailable = 4,
+} ErrorCode;
+
+BOOL ErrorCodeIsValidValue(ErrorCode value);
+
+typedef enum {
+  CodecTypeSpeex = 0,
+  CodecTypePcmS16Le = 1,
+  CodecTypeH264 = 2,
+  CodecTypeAac = 3,
+  CodecTypeOpus = 4,
+} CodecType;
+
+BOOL CodecTypeIsValidValue(CodecType value);
+
+typedef enum {
+  HelloProtocolVersionVersion1 = 1,
+  HelloProtocolVersionVersion2 = 2,
+  HelloProtocolVersionVersion3 = 3,
+} HelloProtocolVersion;
+
+BOOL HelloProtocolVersionIsValidValue(HelloProtocolVersion value);
+
+typedef enum {
+  StartPlaybackProfileNotFoundActionRedirect = 0,
+  StartPlaybackProfileNotFoundActionUseNextAvailable = 1,
+} StartPlaybackProfileNotFoundAction;
+
+BOOL StartPlaybackProfileNotFoundActionIsValidValue(StartPlaybackProfileNotFoundAction value);
+
+typedef enum {
+  PlaybackEndReasonErrorTimeNotAvailable = 1,
+  PlaybackEndReasonErrorProfileNotAvailable = 2,
+  PlaybackEndReasonErrorTranscodeNotAvailable = 3,
+  PlaybackEndReasonPlayEndSessionComplete = 128,
+} PlaybackEndReason;
+
+BOOL PlaybackEndReasonIsValidValue(PlaybackEndReason value);
+
+
+@interface NexustalkRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface Ping : PBGeneratedMessage {
+@private
+}
+
++ (Ping*) defaultInstance;
+- (Ping*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PingBuilder*) builder;
++ (PingBuilder*) builder;
++ (PingBuilder*) builderWithPrototype:(Ping*) prototype;
+- (PingBuilder*) toBuilder;
+
++ (Ping*) parseFromData:(NSData*) data;
++ (Ping*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Ping*) parseFromInputStream:(NSInputStream*) input;
++ (Ping*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Ping*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Ping*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PingBuilder : PBGeneratedMessageBuilder {
+@private
+  Ping* result;
+}
+
+- (Ping*) defaultInstance;
+
+- (PingBuilder*) clear;
+- (PingBuilder*) clone;
+
+- (Ping*) build;
+- (Ping*) buildPartial;
+
+- (PingBuilder*) mergeFrom:(Ping*) other;
+- (PingBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PingBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface Hello : PBGeneratedMessage {
+@private
+  BOOL hasRequireConnectedCamera_:1;
+  BOOL hasIsCamera_:1;
+  BOOL hasUuid_:1;
+  BOOL hasSessionToken_:1;
+  BOOL hasDeviceId_:1;
+  BOOL hasUserAgent_:1;
+  BOOL hasProtocolVersion_:1;
+  BOOL requireConnectedCamera_:1;
+  BOOL isCamera_:1;
+  NSString* uuid;
+  NSString* sessionToken;
+  NSString* deviceId;
+  NSString* userAgent;
+  HelloProtocolVersion protocolVersion;
+}
+- (BOOL) hasProtocolVersion;
+- (BOOL) hasUuid;
+- (BOOL) hasRequireConnectedCamera;
+- (BOOL) hasSessionToken;
+- (BOOL) hasIsCamera;
+- (BOOL) hasDeviceId;
+- (BOOL) hasUserAgent;
+@property (readonly) HelloProtocolVersion protocolVersion;
+@property (readonly, strong) NSString* uuid;
+- (BOOL) requireConnectedCamera;
+@property (readonly, strong) NSString* sessionToken;
+- (BOOL) isCamera;
+@property (readonly, strong) NSString* deviceId;
+@property (readonly, strong) NSString* userAgent;
+
++ (Hello*) defaultInstance;
+- (Hello*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (HelloBuilder*) builder;
++ (HelloBuilder*) builder;
++ (HelloBuilder*) builderWithPrototype:(Hello*) prototype;
+- (HelloBuilder*) toBuilder;
+
++ (Hello*) parseFromData:(NSData*) data;
++ (Hello*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Hello*) parseFromInputStream:(NSInputStream*) input;
++ (Hello*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Hello*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Hello*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface HelloBuilder : PBGeneratedMessageBuilder {
+@private
+  Hello* result;
+}
+
+- (Hello*) defaultInstance;
+
+- (HelloBuilder*) clear;
+- (HelloBuilder*) clone;
+
+- (Hello*) build;
+- (Hello*) buildPartial;
+
+- (HelloBuilder*) mergeFrom:(Hello*) other;
+- (HelloBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (HelloBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasProtocolVersion;
+- (HelloProtocolVersion) protocolVersion;
+- (HelloBuilder*) setProtocolVersion:(HelloProtocolVersion) value;
+- (HelloBuilder*) clearProtocolVersion;
+
+- (BOOL) hasUuid;
+- (NSString*) uuid;
+- (HelloBuilder*) setUuid:(NSString*) value;
+- (HelloBuilder*) clearUuid;
+
+- (BOOL) hasRequireConnectedCamera;
+- (BOOL) requireConnectedCamera;
+- (HelloBuilder*) setRequireConnectedCamera:(BOOL) value;
+- (HelloBuilder*) clearRequireConnectedCamera;
+
+- (BOOL) hasSessionToken;
+- (NSString*) sessionToken;
+- (HelloBuilder*) setSessionToken:(NSString*) value;
+- (HelloBuilder*) clearSessionToken;
+
+- (BOOL) hasIsCamera;
+- (BOOL) isCamera;
+- (HelloBuilder*) setIsCamera:(BOOL) value;
+- (HelloBuilder*) clearIsCamera;
+
+- (BOOL) hasDeviceId;
+- (NSString*) deviceId;
+- (HelloBuilder*) setDeviceId:(NSString*) value;
+- (HelloBuilder*) clearDeviceId;
+
+- (BOOL) hasUserAgent;
+- (NSString*) userAgent;
+- (HelloBuilder*) setUserAgent:(NSString*) value;
+- (HelloBuilder*) clearUserAgent;
+@end
+
+@interface Ok : PBGeneratedMessage {
+@private
+  BOOL hasUdpPort_:1;
+  UInt32 udpPort;
+}
+- (BOOL) hasUdpPort;
+@property (readonly) UInt32 udpPort;
+
++ (Ok*) defaultInstance;
+- (Ok*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (OkBuilder*) builder;
++ (OkBuilder*) builder;
++ (OkBuilder*) builderWithPrototype:(Ok*) prototype;
+- (OkBuilder*) toBuilder;
+
++ (Ok*) parseFromData:(NSData*) data;
++ (Ok*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Ok*) parseFromInputStream:(NSInputStream*) input;
++ (Ok*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Ok*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Ok*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface OkBuilder : PBGeneratedMessageBuilder {
+@private
+  Ok* result;
+}
+
+- (Ok*) defaultInstance;
+
+- (OkBuilder*) clear;
+- (OkBuilder*) clone;
+
+- (Ok*) build;
+- (Ok*) buildPartial;
+
+- (OkBuilder*) mergeFrom:(Ok*) other;
+- (OkBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (OkBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasUdpPort;
+- (UInt32) udpPort;
+- (OkBuilder*) setUdpPort:(UInt32) value;
+- (OkBuilder*) clearUdpPort;
+@end
+
+@interface Error : PBGeneratedMessage {
+@private
+  BOOL hasMessage_:1;
+  BOOL hasCode_:1;
+  NSString* message;
+  ErrorCode code;
+}
+- (BOOL) hasCode;
+- (BOOL) hasMessage;
+@property (readonly) ErrorCode code;
+@property (readonly, strong) NSString* message;
+
++ (Error*) defaultInstance;
+- (Error*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ErrorBuilder*) builder;
++ (ErrorBuilder*) builder;
++ (ErrorBuilder*) builderWithPrototype:(Error*) prototype;
+- (ErrorBuilder*) toBuilder;
+
++ (Error*) parseFromData:(NSData*) data;
++ (Error*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Error*) parseFromInputStream:(NSInputStream*) input;
++ (Error*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Error*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Error*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ErrorBuilder : PBGeneratedMessageBuilder {
+@private
+  Error* result;
+}
+
+- (Error*) defaultInstance;
+
+- (ErrorBuilder*) clear;
+- (ErrorBuilder*) clone;
+
+- (Error*) build;
+- (Error*) buildPartial;
+
+- (ErrorBuilder*) mergeFrom:(Error*) other;
+- (ErrorBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ErrorBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasCode;
+- (ErrorCode) code;
+- (ErrorBuilder*) setCode:(ErrorCode) value;
+- (ErrorBuilder*) clearCode;
+
+- (BOOL) hasMessage;
+- (NSString*) message;
+- (ErrorBuilder*) setMessage:(NSString*) value;
+- (ErrorBuilder*) clearMessage;
+@end
+
+@interface PingCamera : PBGeneratedMessage {
+@private
+}
+
++ (PingCamera*) defaultInstance;
+- (PingCamera*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PingCameraBuilder*) builder;
++ (PingCameraBuilder*) builder;
++ (PingCameraBuilder*) builderWithPrototype:(PingCamera*) prototype;
+- (PingCameraBuilder*) toBuilder;
+
++ (PingCamera*) parseFromData:(NSData*) data;
++ (PingCamera*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PingCamera*) parseFromInputStream:(NSInputStream*) input;
++ (PingCamera*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PingCamera*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PingCamera*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PingCameraBuilder : PBGeneratedMessageBuilder {
+@private
+  PingCamera* result;
+}
+
+- (PingCamera*) defaultInstance;
+
+- (PingCameraBuilder*) clear;
+- (PingCameraBuilder*) clone;
+
+- (PingCamera*) build;
+- (PingCamera*) buildPartial;
+
+- (PingCameraBuilder*) mergeFrom:(PingCamera*) other;
+- (PingCameraBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PingCameraBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface AudioPayload : PBGeneratedMessage {
+@private
+  BOOL hasPayload_:1;
+  BOOL hasSessionId_:1;
+  BOOL hasSampleRate_:1;
+  BOOL hasCodec_:1;
+  NSData* payload;
+  UInt32 sessionId;
+  UInt32 sampleRate;
+  CodecType codec;
+}
+- (BOOL) hasPayload;
+- (BOOL) hasSessionId;
+- (BOOL) hasCodec;
+- (BOOL) hasSampleRate;
+@property (readonly, strong) NSData* payload;
+@property (readonly) UInt32 sessionId;
+@property (readonly) CodecType codec;
+@property (readonly) UInt32 sampleRate;
+
++ (AudioPayload*) defaultInstance;
+- (AudioPayload*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (AudioPayloadBuilder*) builder;
++ (AudioPayloadBuilder*) builder;
++ (AudioPayloadBuilder*) builderWithPrototype:(AudioPayload*) prototype;
+- (AudioPayloadBuilder*) toBuilder;
+
++ (AudioPayload*) parseFromData:(NSData*) data;
++ (AudioPayload*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (AudioPayload*) parseFromInputStream:(NSInputStream*) input;
++ (AudioPayload*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (AudioPayload*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (AudioPayload*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface AudioPayloadBuilder : PBGeneratedMessageBuilder {
+@private
+  AudioPayload* result;
+}
+
+- (AudioPayload*) defaultInstance;
+
+- (AudioPayloadBuilder*) clear;
+- (AudioPayloadBuilder*) clone;
+
+- (AudioPayload*) build;
+- (AudioPayload*) buildPartial;
+
+- (AudioPayloadBuilder*) mergeFrom:(AudioPayload*) other;
+- (AudioPayloadBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (AudioPayloadBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasPayload;
+- (NSData*) payload;
+- (AudioPayloadBuilder*) setPayload:(NSData*) value;
+- (AudioPayloadBuilder*) clearPayload;
+
+- (BOOL) hasSessionId;
+- (UInt32) sessionId;
+- (AudioPayloadBuilder*) setSessionId:(UInt32) value;
+- (AudioPayloadBuilder*) clearSessionId;
+
+- (BOOL) hasCodec;
+- (CodecType) codec;
+- (AudioPayloadBuilder*) setCodec:(CodecType) value;
+- (AudioPayloadBuilder*) clearCodec;
+
+- (BOOL) hasSampleRate;
+- (UInt32) sampleRate;
+- (AudioPayloadBuilder*) setSampleRate:(UInt32) value;
+- (AudioPayloadBuilder*) clearSampleRate;
+@end
+
+@interface StartPlayback : PBGeneratedMessage {
+@private
+  BOOL hasStartTime_:1;
+  BOOL hasExternalIp_:1;
+  BOOL hasSessionId_:1;
+  BOOL hasExternalPort_:1;
+  BOOL hasProfile_:1;
+  BOOL hasProfileNotFoundAction_:1;
+  Float64 startTime;
+  NSData* externalIp;
+  UInt32 sessionId;
+  UInt32 externalPort;
+  CT_AVProfile profile;
+  StartPlaybackProfileNotFoundAction profileNotFoundAction;
+  PBAppendableArray * otherProfilesArray;
+}
+- (BOOL) hasSessionId;
+- (BOOL) hasProfile;
+- (BOOL) hasStartTime;
+- (BOOL) hasExternalIp;
+- (BOOL) hasExternalPort;
+- (BOOL) hasProfileNotFoundAction;
+@property (readonly) UInt32 sessionId;
+@property (readonly) CT_AVProfile profile;
+@property (readonly) Float64 startTime;
+@property (readonly, strong) NSData* externalIp;
+@property (readonly) UInt32 externalPort;
+@property (readonly, strong) PBArray * otherProfiles;
+@property (readonly) StartPlaybackProfileNotFoundAction profileNotFoundAction;
+- (CT_AVProfile)otherProfilesAtIndex:(NSUInteger)index;
+
++ (StartPlayback*) defaultInstance;
+- (StartPlayback*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (StartPlaybackBuilder*) builder;
++ (StartPlaybackBuilder*) builder;
++ (StartPlaybackBuilder*) builderWithPrototype:(StartPlayback*) prototype;
+- (StartPlaybackBuilder*) toBuilder;
+
++ (StartPlayback*) parseFromData:(NSData*) data;
++ (StartPlayback*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (StartPlayback*) parseFromInputStream:(NSInputStream*) input;
++ (StartPlayback*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (StartPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (StartPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface StartPlaybackBuilder : PBGeneratedMessageBuilder {
+@private
+  StartPlayback* result;
+}
+
+- (StartPlayback*) defaultInstance;
+
+- (StartPlaybackBuilder*) clear;
+- (StartPlaybackBuilder*) clone;
+
+- (StartPlayback*) build;
+- (StartPlayback*) buildPartial;
+
+- (StartPlaybackBuilder*) mergeFrom:(StartPlayback*) other;
+- (StartPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (StartPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasSessionId;
+- (UInt32) sessionId;
+- (StartPlaybackBuilder*) setSessionId:(UInt32) value;
+- (StartPlaybackBuilder*) clearSessionId;
+
+- (BOOL) hasProfile;
+- (CT_AVProfile) profile;
+- (StartPlaybackBuilder*) setProfile:(CT_AVProfile) value;
+- (StartPlaybackBuilder*) clearProfile;
+
+- (BOOL) hasStartTime;
+- (Float64) startTime;
+- (StartPlaybackBuilder*) setStartTime:(Float64) value;
+- (StartPlaybackBuilder*) clearStartTime;
+
+- (BOOL) hasExternalIp;
+- (NSData*) externalIp;
+- (StartPlaybackBuilder*) setExternalIp:(NSData*) value;
+- (StartPlaybackBuilder*) clearExternalIp;
+
+- (BOOL) hasExternalPort;
+- (UInt32) externalPort;
+- (StartPlaybackBuilder*) setExternalPort:(UInt32) value;
+- (StartPlaybackBuilder*) clearExternalPort;
+
+- (PBAppendableArray *)otherProfiles;
+- (CT_AVProfile)otherProfilesAtIndex:(NSUInteger)index;
+- (StartPlaybackBuilder *)addOtherProfiles:(CT_AVProfile)value;
+- (StartPlaybackBuilder *)setOtherProfilesArray:(NSArray *)array;
+- (StartPlaybackBuilder *)setOtherProfilesValues:(const CT_AVProfile *)values count:(NSUInteger)count;
+- (StartPlaybackBuilder *)clearOtherProfiles;
+
+- (BOOL) hasProfileNotFoundAction;
+- (StartPlaybackProfileNotFoundAction) profileNotFoundAction;
+- (StartPlaybackBuilder*) setProfileNotFoundAction:(StartPlaybackProfileNotFoundAction) value;
+- (StartPlaybackBuilder*) clearProfileNotFoundAction;
+@end
+
+@interface StopPlayback : PBGeneratedMessage {
+@private
+  BOOL hasSessionId_:1;
+  UInt32 sessionId;
+}
+- (BOOL) hasSessionId;
+@property (readonly) UInt32 sessionId;
+
++ (StopPlayback*) defaultInstance;
+- (StopPlayback*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (StopPlaybackBuilder*) builder;
++ (StopPlaybackBuilder*) builder;
++ (StopPlaybackBuilder*) builderWithPrototype:(StopPlayback*) prototype;
+- (StopPlaybackBuilder*) toBuilder;
+
++ (StopPlayback*) parseFromData:(NSData*) data;
++ (StopPlayback*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (StopPlayback*) parseFromInputStream:(NSInputStream*) input;
++ (StopPlayback*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (StopPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (StopPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface StopPlaybackBuilder : PBGeneratedMessageBuilder {
+@private
+  StopPlayback* result;
+}
+
+- (StopPlayback*) defaultInstance;
+
+- (StopPlaybackBuilder*) clear;
+- (StopPlaybackBuilder*) clone;
+
+- (StopPlayback*) build;
+- (StopPlayback*) buildPartial;
+
+- (StopPlaybackBuilder*) mergeFrom:(StopPlayback*) other;
+- (StopPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (StopPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasSessionId;
+- (UInt32) sessionId;
+- (StopPlaybackBuilder*) setSessionId:(UInt32) value;
+- (StopPlaybackBuilder*) clearSessionId;
+@end
+
+@interface PlaybackBegin : PBGeneratedMessage {
+@private
+  BOOL hasSrtpMasterKey_:1;
+  BOOL hasSrtpMasterSalt_:1;
+  BOOL hasSessionId_:1;
+  BOOL hasFecKVal_:1;
+  BOOL hasFecNVal_:1;
+  NSData* srtpMasterKey;
+  NSData* srtpMasterSalt;
+  UInt32 sessionId;
+  UInt32 fecKVal;
+  UInt32 fecNVal;
+  NSMutableArray * channelsArray;
+}
+- (BOOL) hasSessionId;
+- (BOOL) hasSrtpMasterKey;
+- (BOOL) hasSrtpMasterSalt;
+- (BOOL) hasFecKVal;
+- (BOOL) hasFecNVal;
+@property (readonly) UInt32 sessionId;
+@property (readonly, strong) NSArray * channels;
+@property (readonly, strong) NSData* srtpMasterKey;
+@property (readonly, strong) NSData* srtpMasterSalt;
+@property (readonly) UInt32 fecKVal;
+@property (readonly) UInt32 fecNVal;
+- (PlaybackBeginStream*)channelsAtIndex:(NSUInteger)index;
+
++ (PlaybackBegin*) defaultInstance;
+- (PlaybackBegin*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PlaybackBeginBuilder*) builder;
++ (PlaybackBeginBuilder*) builder;
++ (PlaybackBeginBuilder*) builderWithPrototype:(PlaybackBegin*) prototype;
+- (PlaybackBeginBuilder*) toBuilder;
+
++ (PlaybackBegin*) parseFromData:(NSData*) data;
++ (PlaybackBegin*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackBegin*) parseFromInputStream:(NSInputStream*) input;
++ (PlaybackBegin*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PlaybackBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PlaybackBeginStream : PBGeneratedMessage {
+@private
+  BOOL hasStartTime_:1;
+  BOOL hasChannelId_:1;
+  BOOL hasSampleRate_:1;
+  BOOL hasUdpSsrc_:1;
+  BOOL hasRtpStartTime_:1;
+  BOOL hasCodecType_:1;
+  BOOL hasProfile_:1;
+  Float64 startTime;
+  UInt32 channelId;
+  UInt32 sampleRate;
+  UInt32 udpSsrc;
+  UInt32 rtpStartTime;
+  CodecType codecType;
+  CT_AVProfile profile;
+  NSMutableArray * privateDataArray;
+}
+- (BOOL) hasChannelId;
+- (BOOL) hasCodecType;
+- (BOOL) hasSampleRate;
+- (BOOL) hasStartTime;
+- (BOOL) hasUdpSsrc;
+- (BOOL) hasRtpStartTime;
+- (BOOL) hasProfile;
+@property (readonly) UInt32 channelId;
+@property (readonly) CodecType codecType;
+@property (readonly) UInt32 sampleRate;
+@property (readonly, strong) PBArray * privateData;
+@property (readonly) Float64 startTime;
+@property (readonly) UInt32 udpSsrc;
+@property (readonly) UInt32 rtpStartTime;
+@property (readonly) CT_AVProfile profile;
+- (NSData*)privateDataAtIndex:(NSUInteger)index;
+
++ (PlaybackBeginStream*) defaultInstance;
+- (PlaybackBeginStream*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PlaybackBeginStreamBuilder*) builder;
++ (PlaybackBeginStreamBuilder*) builder;
++ (PlaybackBeginStreamBuilder*) builderWithPrototype:(PlaybackBeginStream*) prototype;
+- (PlaybackBeginStreamBuilder*) toBuilder;
+
++ (PlaybackBeginStream*) parseFromData:(NSData*) data;
++ (PlaybackBeginStream*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackBeginStream*) parseFromInputStream:(NSInputStream*) input;
++ (PlaybackBeginStream*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackBeginStream*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PlaybackBeginStream*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PlaybackBeginStreamBuilder : PBGeneratedMessageBuilder {
+@private
+  PlaybackBeginStream* result;
+}
+
+- (PlaybackBeginStream*) defaultInstance;
+
+- (PlaybackBeginStreamBuilder*) clear;
+- (PlaybackBeginStreamBuilder*) clone;
+
+- (PlaybackBeginStream*) build;
+- (PlaybackBeginStream*) buildPartial;
+
+- (PlaybackBeginStreamBuilder*) mergeFrom:(PlaybackBeginStream*) other;
+- (PlaybackBeginStreamBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PlaybackBeginStreamBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasChannelId;
+- (UInt32) channelId;
+- (PlaybackBeginStreamBuilder*) setChannelId:(UInt32) value;
+- (PlaybackBeginStreamBuilder*) clearChannelId;
+
+- (BOOL) hasCodecType;
+- (CodecType) codecType;
+- (PlaybackBeginStreamBuilder*) setCodecType:(CodecType) value;
+- (PlaybackBeginStreamBuilder*) clearCodecType;
+
+- (BOOL) hasSampleRate;
+- (UInt32) sampleRate;
+- (PlaybackBeginStreamBuilder*) setSampleRate:(UInt32) value;
+- (PlaybackBeginStreamBuilder*) clearSampleRate;
+
+- (NSMutableArray *)privateData;
+- (NSData*)privateDataAtIndex:(NSUInteger)index;
+- (PlaybackBeginStreamBuilder *)addPrivateData:(NSData*)value;
+- (PlaybackBeginStreamBuilder *)setPrivateDataArray:(NSArray *)array;
+- (PlaybackBeginStreamBuilder *)clearPrivateData;
+
+- (BOOL) hasStartTime;
+- (Float64) startTime;
+- (PlaybackBeginStreamBuilder*) setStartTime:(Float64) value;
+- (PlaybackBeginStreamBuilder*) clearStartTime;
+
+- (BOOL) hasUdpSsrc;
+- (UInt32) udpSsrc;
+- (PlaybackBeginStreamBuilder*) setUdpSsrc:(UInt32) value;
+- (PlaybackBeginStreamBuilder*) clearUdpSsrc;
+
+- (BOOL) hasRtpStartTime;
+- (UInt32) rtpStartTime;
+- (PlaybackBeginStreamBuilder*) setRtpStartTime:(UInt32) value;
+- (PlaybackBeginStreamBuilder*) clearRtpStartTime;
+
+- (BOOL) hasProfile;
+- (CT_AVProfile) profile;
+- (PlaybackBeginStreamBuilder*) setProfile:(CT_AVProfile) value;
+- (PlaybackBeginStreamBuilder*) clearProfile;
+@end
+
+@interface PlaybackBeginBuilder : PBGeneratedMessageBuilder {
+@private
+  PlaybackBegin* result;
+}
+
+- (PlaybackBegin*) defaultInstance;
+
+- (PlaybackBeginBuilder*) clear;
+- (PlaybackBeginBuilder*) clone;
+
+- (PlaybackBegin*) build;
+- (PlaybackBegin*) buildPartial;
+
+- (PlaybackBeginBuilder*) mergeFrom:(PlaybackBegin*) other;
+- (PlaybackBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PlaybackBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasSessionId;
+- (UInt32) sessionId;
+- (PlaybackBeginBuilder*) setSessionId:(UInt32) value;
+- (PlaybackBeginBuilder*) clearSessionId;
+
+- (NSMutableArray *)channels;
+- (PlaybackBeginStream*)channelsAtIndex:(NSUInteger)index;
+- (PlaybackBeginBuilder *)addChannels:(PlaybackBeginStream*)value;
+- (PlaybackBeginBuilder *)setChannelsArray:(NSArray *)array;
+- (PlaybackBeginBuilder *)clearChannels;
+
+- (BOOL) hasSrtpMasterKey;
+- (NSData*) srtpMasterKey;
+- (PlaybackBeginBuilder*) setSrtpMasterKey:(NSData*) value;
+- (PlaybackBeginBuilder*) clearSrtpMasterKey;
+
+- (BOOL) hasSrtpMasterSalt;
+- (NSData*) srtpMasterSalt;
+- (PlaybackBeginBuilder*) setSrtpMasterSalt:(NSData*) value;
+- (PlaybackBeginBuilder*) clearSrtpMasterSalt;
+
+- (BOOL) hasFecKVal;
+- (UInt32) fecKVal;
+- (PlaybackBeginBuilder*) setFecKVal:(UInt32) value;
+- (PlaybackBeginBuilder*) clearFecKVal;
+
+- (BOOL) hasFecNVal;
+- (UInt32) fecNVal;
+- (PlaybackBeginBuilder*) setFecNVal:(UInt32) value;
+- (PlaybackBeginBuilder*) clearFecNVal;
+@end
+
+@interface PlaybackEnd : PBGeneratedMessage {
+@private
+  BOOL hasSessionId_:1;
+  BOOL hasReason_:1;
+  UInt32 sessionId;
+  PlaybackEndReason reason;
+}
+- (BOOL) hasSessionId;
+- (BOOL) hasReason;
+@property (readonly) UInt32 sessionId;
+@property (readonly) PlaybackEndReason reason;
+
++ (PlaybackEnd*) defaultInstance;
+- (PlaybackEnd*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PlaybackEndBuilder*) builder;
++ (PlaybackEndBuilder*) builder;
++ (PlaybackEndBuilder*) builderWithPrototype:(PlaybackEnd*) prototype;
+- (PlaybackEndBuilder*) toBuilder;
+
++ (PlaybackEnd*) parseFromData:(NSData*) data;
++ (PlaybackEnd*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackEnd*) parseFromInputStream:(NSInputStream*) input;
++ (PlaybackEnd*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackEnd*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PlaybackEnd*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PlaybackEndBuilder : PBGeneratedMessageBuilder {
+@private
+  PlaybackEnd* result;
+}
+
+- (PlaybackEnd*) defaultInstance;
+
+- (PlaybackEndBuilder*) clear;
+- (PlaybackEndBuilder*) clone;
+
+- (PlaybackEnd*) build;
+- (PlaybackEnd*) buildPartial;
+
+- (PlaybackEndBuilder*) mergeFrom:(PlaybackEnd*) other;
+- (PlaybackEndBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PlaybackEndBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasSessionId;
+- (UInt32) sessionId;
+- (PlaybackEndBuilder*) setSessionId:(UInt32) value;
+- (PlaybackEndBuilder*) clearSessionId;
+
+- (BOOL) hasReason;
+- (PlaybackEndReason) reason;
+- (PlaybackEndBuilder*) setReason:(PlaybackEndReason) value;
+- (PlaybackEndBuilder*) clearReason;
+@end
+
+@interface PlaybackPacket : PBGeneratedMessage {
+@private
+  BOOL hasPayload_:1;
+  BOOL hasSessionId_:1;
+  BOOL hasChannelId_:1;
+  BOOL hasLatencyRtpSequence_:1;
+  BOOL hasLatencyRtpSsrc_:1;
+  BOOL hasTimestampDelta_:1;
+  NSData* payload;
+  UInt32 sessionId;
+  UInt32 channelId;
+  UInt32 latencyRtpSequence;
+  UInt32 latencyRtpSsrc;
+  SInt32 timestampDelta;
+}
+- (BOOL) hasSessionId;
+- (BOOL) hasChannelId;
+- (BOOL) hasTimestampDelta;
+- (BOOL) hasPayload;
+- (BOOL) hasLatencyRtpSequence;
+- (BOOL) hasLatencyRtpSsrc;
+@property (readonly) UInt32 sessionId;
+@property (readonly) UInt32 channelId;
+@property (readonly) SInt32 timestampDelta;
+@property (readonly, strong) NSData* payload;
+@property (readonly) UInt32 latencyRtpSequence;
+@property (readonly) UInt32 latencyRtpSsrc;
+
++ (PlaybackPacket*) defaultInstance;
+- (PlaybackPacket*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PlaybackPacketBuilder*) builder;
++ (PlaybackPacketBuilder*) builder;
++ (PlaybackPacketBuilder*) builderWithPrototype:(PlaybackPacket*) prototype;
+- (PlaybackPacketBuilder*) toBuilder;
+
++ (PlaybackPacket*) parseFromData:(NSData*) data;
++ (PlaybackPacket*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackPacket*) parseFromInputStream:(NSInputStream*) input;
++ (PlaybackPacket*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PlaybackPacket*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PlaybackPacket*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PlaybackPacketBuilder : PBGeneratedMessageBuilder {
+@private
+  PlaybackPacket* result;
+}
+
+- (PlaybackPacket*) defaultInstance;
+
+- (PlaybackPacketBuilder*) clear;
+- (PlaybackPacketBuilder*) clone;
+
+- (PlaybackPacket*) build;
+- (PlaybackPacket*) buildPartial;
+
+- (PlaybackPacketBuilder*) mergeFrom:(PlaybackPacket*) other;
+- (PlaybackPacketBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PlaybackPacketBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasSessionId;
+- (UInt32) sessionId;
+- (PlaybackPacketBuilder*) setSessionId:(UInt32) value;
+- (PlaybackPacketBuilder*) clearSessionId;
+
+- (BOOL) hasChannelId;
+- (UInt32) channelId;
+- (PlaybackPacketBuilder*) setChannelId:(UInt32) value;
+- (PlaybackPacketBuilder*) clearChannelId;
+
+- (BOOL) hasTimestampDelta;
+- (SInt32) timestampDelta;
+- (PlaybackPacketBuilder*) setTimestampDelta:(SInt32) value;
+- (PlaybackPacketBuilder*) clearTimestampDelta;
+
+- (BOOL) hasPayload;
+- (NSData*) payload;
+- (PlaybackPacketBuilder*) setPayload:(NSData*) value;
+- (PlaybackPacketBuilder*) clearPayload;
+
+- (BOOL) hasLatencyRtpSequence;
+- (UInt32) latencyRtpSequence;
+- (PlaybackPacketBuilder*) setLatencyRtpSequence:(UInt32) value;
+- (PlaybackPacketBuilder*) clearLatencyRtpSequence;
+
+- (BOOL) hasLatencyRtpSsrc;
+- (UInt32) latencyRtpSsrc;
+- (PlaybackPacketBuilder*) setLatencyRtpSsrc:(UInt32) value;
+- (PlaybackPacketBuilder*) clearLatencyRtpSsrc;
+@end
+
+@interface ClockSync : PBGeneratedMessage {
+@private
+  BOOL hasServerSystemTimeSec_:1;
+  BOOL hasServerSystemTimeMsec_:1;
+  UInt32 serverSystemTimeSec;
+  UInt32 serverSystemTimeMsec;
+}
+- (BOOL) hasServerSystemTimeSec;
+- (BOOL) hasServerSystemTimeMsec;
+@property (readonly) UInt32 serverSystemTimeSec;
+@property (readonly) UInt32 serverSystemTimeMsec;
+
++ (ClockSync*) defaultInstance;
+- (ClockSync*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ClockSyncBuilder*) builder;
++ (ClockSyncBuilder*) builder;
++ (ClockSyncBuilder*) builderWithPrototype:(ClockSync*) prototype;
+- (ClockSyncBuilder*) toBuilder;
+
++ (ClockSync*) parseFromData:(NSData*) data;
++ (ClockSync*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ClockSync*) parseFromInputStream:(NSInputStream*) input;
++ (ClockSync*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ClockSync*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ClockSync*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ClockSyncBuilder : PBGeneratedMessageBuilder {
+@private
+  ClockSync* result;
+}
+
+- (ClockSync*) defaultInstance;
+
+- (ClockSyncBuilder*) clear;
+- (ClockSyncBuilder*) clone;
+
+- (ClockSync*) build;
+- (ClockSync*) buildPartial;
+
+- (ClockSyncBuilder*) mergeFrom:(ClockSync*) other;
+- (ClockSyncBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ClockSyncBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasServerSystemTimeSec;
+- (UInt32) serverSystemTimeSec;
+- (ClockSyncBuilder*) setServerSystemTimeSec:(UInt32) value;
+- (ClockSyncBuilder*) clearServerSystemTimeSec;
+
+- (BOOL) hasServerSystemTimeMsec;
+- (UInt32) serverSystemTimeMsec;
+- (ClockSyncBuilder*) setServerSystemTimeMsec:(UInt32) value;
+- (ClockSyncBuilder*) clearServerSystemTimeMsec;
+@end
+
+@interface ClockSyncEcho : PBGeneratedMessage {
+@private
+  BOOL hasServerSystemTimeEchoSec_:1;
+  BOOL hasServerSystemTimeEchoMsec_:1;
+  BOOL hasClientSystemTimeSec_:1;
+  BOOL hasClientSystemTimeMsec_:1;
+  UInt32 serverSystemTimeEchoSec;
+  UInt32 serverSystemTimeEchoMsec;
+  UInt32 clientSystemTimeSec;
+  UInt32 clientSystemTimeMsec;
+}
+- (BOOL) hasServerSystemTimeEchoSec;
+- (BOOL) hasServerSystemTimeEchoMsec;
+- (BOOL) hasClientSystemTimeSec;
+- (BOOL) hasClientSystemTimeMsec;
+@property (readonly) UInt32 serverSystemTimeEchoSec;
+@property (readonly) UInt32 serverSystemTimeEchoMsec;
+@property (readonly) UInt32 clientSystemTimeSec;
+@property (readonly) UInt32 clientSystemTimeMsec;
+
++ (ClockSyncEcho*) defaultInstance;
+- (ClockSyncEcho*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ClockSyncEchoBuilder*) builder;
++ (ClockSyncEchoBuilder*) builder;
++ (ClockSyncEchoBuilder*) builderWithPrototype:(ClockSyncEcho*) prototype;
+- (ClockSyncEchoBuilder*) toBuilder;
+
++ (ClockSyncEcho*) parseFromData:(NSData*) data;
++ (ClockSyncEcho*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ClockSyncEcho*) parseFromInputStream:(NSInputStream*) input;
++ (ClockSyncEcho*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ClockSyncEcho*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ClockSyncEcho*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ClockSyncEchoBuilder : PBGeneratedMessageBuilder {
+@private
+  ClockSyncEcho* result;
+}
+
+- (ClockSyncEcho*) defaultInstance;
+
+- (ClockSyncEchoBuilder*) clear;
+- (ClockSyncEchoBuilder*) clone;
+
+- (ClockSyncEcho*) build;
+- (ClockSyncEcho*) buildPartial;
+
+- (ClockSyncEchoBuilder*) mergeFrom:(ClockSyncEcho*) other;
+- (ClockSyncEchoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ClockSyncEchoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasServerSystemTimeEchoSec;
+- (UInt32) serverSystemTimeEchoSec;
+- (ClockSyncEchoBuilder*) setServerSystemTimeEchoSec:(UInt32) value;
+- (ClockSyncEchoBuilder*) clearServerSystemTimeEchoSec;
+
+- (BOOL) hasServerSystemTimeEchoMsec;
+- (UInt32) serverSystemTimeEchoMsec;
+- (ClockSyncEchoBuilder*) setServerSystemTimeEchoMsec:(UInt32) value;
+- (ClockSyncEchoBuilder*) clearServerSystemTimeEchoMsec;
+
+- (BOOL) hasClientSystemTimeSec;
+- (UInt32) clientSystemTimeSec;
+- (ClockSyncEchoBuilder*) setClientSystemTimeSec:(UInt32) value;
+- (ClockSyncEchoBuilder*) clearClientSystemTimeSec;
+
+- (BOOL) hasClientSystemTimeMsec;
+- (UInt32) clientSystemTimeMsec;
+- (ClockSyncEchoBuilder*) setClientSystemTimeMsec:(UInt32) value;
+- (ClockSyncEchoBuilder*) clearClientSystemTimeMsec;
+@end
+
+@interface LatencyMeasure : PBGeneratedMessage {
+@private
+  BOOL hasEarliestTime_:1;
+  BOOL hasLatestTime_:1;
+  BOOL hasLatencyRtpSequence_:1;
+  BOOL hasLatencyRtpSsrc_:1;
+  UInt64 earliestTime;
+  UInt64 latestTime;
+  UInt32 latencyRtpSequence;
+  UInt32 latencyRtpSsrc;
+}
+- (BOOL) hasEarliestTime;
+- (BOOL) hasLatestTime;
+- (BOOL) hasLatencyRtpSequence;
+- (BOOL) hasLatencyRtpSsrc;
+@property (readonly) UInt64 earliestTime;
+@property (readonly) UInt64 latestTime;
+@property (readonly) UInt32 latencyRtpSequence;
+@property (readonly) UInt32 latencyRtpSsrc;
+
++ (LatencyMeasure*) defaultInstance;
+- (LatencyMeasure*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (LatencyMeasureBuilder*) builder;
++ (LatencyMeasureBuilder*) builder;
++ (LatencyMeasureBuilder*) builderWithPrototype:(LatencyMeasure*) prototype;
+- (LatencyMeasureBuilder*) toBuilder;
+
++ (LatencyMeasure*) parseFromData:(NSData*) data;
++ (LatencyMeasure*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (LatencyMeasure*) parseFromInputStream:(NSInputStream*) input;
++ (LatencyMeasure*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (LatencyMeasure*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (LatencyMeasure*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface LatencyMeasureBuilder : PBGeneratedMessageBuilder {
+@private
+  LatencyMeasure* result;
+}
+
+- (LatencyMeasure*) defaultInstance;
+
+- (LatencyMeasureBuilder*) clear;
+- (LatencyMeasureBuilder*) clone;
+
+- (LatencyMeasure*) build;
+- (LatencyMeasure*) buildPartial;
+
+- (LatencyMeasureBuilder*) mergeFrom:(LatencyMeasure*) other;
+- (LatencyMeasureBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (LatencyMeasureBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasEarliestTime;
+- (UInt64) earliestTime;
+- (LatencyMeasureBuilder*) setEarliestTime:(UInt64) value;
+- (LatencyMeasureBuilder*) clearEarliestTime;
+
+- (BOOL) hasLatestTime;
+- (UInt64) latestTime;
+- (LatencyMeasureBuilder*) setLatestTime:(UInt64) value;
+- (LatencyMeasureBuilder*) clearLatestTime;
+
+- (BOOL) hasLatencyRtpSequence;
+- (UInt32) latencyRtpSequence;
+- (LatencyMeasureBuilder*) setLatencyRtpSequence:(UInt32) value;
+- (LatencyMeasureBuilder*) clearLatencyRtpSequence;
+
+- (BOOL) hasLatencyRtpSsrc;
+- (UInt32) latencyRtpSsrc;
+- (LatencyMeasureBuilder*) setLatencyRtpSsrc:(UInt32) value;
+- (LatencyMeasureBuilder*) clearLatencyRtpSsrc;
+@end
+
+@interface Redirect : PBGeneratedMessage {
+@private
+  BOOL hasNewHost_:1;
+  NSString* newHost;
+}
+- (BOOL) hasNewHost;
+@property (readonly, strong) NS_RETURNS_NOT_RETAINED NSString* newHost;
+
++ (Redirect*) defaultInstance;
+- (Redirect*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (RedirectBuilder*) builder;
++ (RedirectBuilder*) builder;
++ (RedirectBuilder*) builderWithPrototype:(Redirect*) prototype;
+- (RedirectBuilder*) toBuilder;
+
++ (Redirect*) parseFromData:(NSData*) data;
++ (Redirect*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Redirect*) parseFromInputStream:(NSInputStream*) input;
++ (Redirect*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Redirect*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Redirect*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface RedirectBuilder : PBGeneratedMessageBuilder {
+@private
+  Redirect* result;
+}
+
+- (Redirect*) defaultInstance;
+
+- (RedirectBuilder*) clear;
+- (RedirectBuilder*) clone;
+
+- (Redirect*) build;
+- (Redirect*) buildPartial;
+
+- (RedirectBuilder*) mergeFrom:(Redirect*) other;
+- (RedirectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (RedirectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasNewHost;
+- (NSString*) newHost NS_RETURNS_NOT_RETAINED;
+- (RedirectBuilder*) setNewHost:(NSString*) value;
+- (RedirectBuilder*) clearNewHost;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Nexustalk.pb.m b/src/gen_proto/Nexustalk.pb.m
new file mode 100644
index 0000000..43e8c5f
--- /dev/null
+++ b/src/gen_proto/Nexustalk.pb.m
@@ -0,0 +1,5275 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Nexustalk.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation NexustalkRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [NexustalkRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    [CommontalkRoot registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+BOOL PacketTypeIsValidValue(PacketType value) {
+  switch (value) {
+    case PacketTypePacketTypePing:
+    case PacketTypePacketTypeHello:
+    case PacketTypePacketTypePingCamera:
+    case PacketTypePacketTypeAudioPayload:
+    case PacketTypePacketTypeStartPlayback:
+    case PacketTypePacketTypeStopPlayback:
+    case PacketTypePacketTypeClockSyncEcho:
+    case PacketTypePacketTypeLatencyMeasure:
+    case PacketTypePacketTypeOk:
+    case PacketTypePacketTypeError:
+    case PacketTypePacketTypePlaybackBegin:
+    case PacketTypePacketTypePlaybackEnd:
+    case PacketTypePacketTypePlaybackPacket:
+    case PacketTypePacketTypeLongPlaybackPacket:
+    case PacketTypePacketTypeClockSync:
+    case PacketTypePacketTypeRedirect:
+      return YES;
+    default:
+      return NO;
+  }
+}
+BOOL ErrorCodeIsValidValue(ErrorCode value) {
+  switch (value) {
+    case ErrorCodeErrorCameraNotConnected:
+    case ErrorCodeErrorIllegalPacket:
+    case ErrorCodeErrorAuthorizationFailed:
+    case ErrorCodeErrorNoTranscoderAvailable:
+      return YES;
+    default:
+      return NO;
+  }
+}
+BOOL CodecTypeIsValidValue(CodecType value) {
+  switch (value) {
+    case CodecTypeSpeex:
+    case CodecTypePcmS16Le:
+    case CodecTypeH264:
+    case CodecTypeAac:
+    case CodecTypeOpus:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface Ping ()
+@end
+
+@implementation Ping
+
+- (id) init {
+  if ((self = [super init])) {
+  }
+  return self;
+}
+static Ping* defaultPingInstance = nil;
++ (void) initialize {
+  if (self == [Ping class]) {
+    defaultPingInstance = [[Ping alloc] init];
+  }
+}
++ (Ping*) defaultInstance {
+  return defaultPingInstance;
+}
+- (Ping*) defaultInstance {
+  return defaultPingInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Ping*) parseFromData:(NSData*) data {
+  return (Ping*)[[[Ping builder] mergeFromData:data] build];
+}
++ (Ping*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Ping*)[[[Ping builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Ping*) parseFromInputStream:(NSInputStream*) input {
+  return (Ping*)[[[Ping builder] mergeFromInputStream:input] build];
+}
++ (Ping*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Ping*)[[[Ping builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Ping*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Ping*)[[[Ping builder] mergeFromCodedInputStream:input] build];
+}
++ (Ping*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Ping*)[[[Ping builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PingBuilder*) builder {
+  return [[PingBuilder alloc] init];
+}
++ (PingBuilder*) builderWithPrototype:(Ping*) prototype {
+  return [[Ping builder] mergeFrom:prototype];
+}
+- (PingBuilder*) builder {
+  return [Ping builder];
+}
+- (PingBuilder*) toBuilder {
+  return [Ping builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Ping class]]) {
+    return NO;
+  }
+  Ping *otherMessage = other;
+  return
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PingBuilder()
+@property (strong) Ping* result;
+@end
+
+@implementation PingBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Ping alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PingBuilder*) clear {
+  self.result = [[Ping alloc] init];
+  return self;
+}
+- (PingBuilder*) clone {
+  return [Ping builderWithPrototype:result];
+}
+- (Ping*) defaultInstance {
+  return [Ping defaultInstance];
+}
+- (Ping*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Ping*) buildPartial {
+  Ping* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PingBuilder*) mergeFrom:(Ping*) other {
+  if (other == [Ping defaultInstance]) {
+    return self;
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PingBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PingBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+    }
+  }
+}
+@end
+
+@interface Hello ()
+@property HelloProtocolVersion protocolVersion;
+@property (strong) NSString* uuid;
+@property BOOL requireConnectedCamera;
+@property (strong) NSString* sessionToken;
+@property BOOL isCamera;
+@property (strong) NSString* deviceId;
+@property (strong) NSString* userAgent;
+@end
+
+@implementation Hello
+
+- (BOOL) hasProtocolVersion {
+  return !!hasProtocolVersion_;
+}
+- (void) setHasProtocolVersion:(BOOL) value_ {
+  hasProtocolVersion_ = !!value_;
+}
+@synthesize protocolVersion;
+- (BOOL) hasUuid {
+  return !!hasUuid_;
+}
+- (void) setHasUuid:(BOOL) value_ {
+  hasUuid_ = !!value_;
+}
+@synthesize uuid;
+- (BOOL) hasRequireConnectedCamera {
+  return !!hasRequireConnectedCamera_;
+}
+- (void) setHasRequireConnectedCamera:(BOOL) value_ {
+  hasRequireConnectedCamera_ = !!value_;
+}
+- (BOOL) requireConnectedCamera {
+  return !!requireConnectedCamera_;
+}
+- (void) setRequireConnectedCamera:(BOOL) value_ {
+  requireConnectedCamera_ = !!value_;
+}
+- (BOOL) hasSessionToken {
+  return !!hasSessionToken_;
+}
+- (void) setHasSessionToken:(BOOL) value_ {
+  hasSessionToken_ = !!value_;
+}
+@synthesize sessionToken;
+- (BOOL) hasIsCamera {
+  return !!hasIsCamera_;
+}
+- (void) setHasIsCamera:(BOOL) value_ {
+  hasIsCamera_ = !!value_;
+}
+- (BOOL) isCamera {
+  return !!isCamera_;
+}
+- (void) setIsCamera:(BOOL) value_ {
+  isCamera_ = !!value_;
+}
+- (BOOL) hasDeviceId {
+  return !!hasDeviceId_;
+}
+- (void) setHasDeviceId:(BOOL) value_ {
+  hasDeviceId_ = !!value_;
+}
+@synthesize deviceId;
+- (BOOL) hasUserAgent {
+  return !!hasUserAgent_;
+}
+- (void) setHasUserAgent:(BOOL) value_ {
+  hasUserAgent_ = !!value_;
+}
+@synthesize userAgent;
+- (id) init {
+  if ((self = [super init])) {
+    self.protocolVersion = HelloProtocolVersionVersion1;
+    self.uuid = @"";
+    self.requireConnectedCamera = NO;
+    self.sessionToken = @"";
+    self.isCamera = NO;
+    self.deviceId = @"";
+    self.userAgent = @"";
+  }
+  return self;
+}
+static Hello* defaultHelloInstance = nil;
++ (void) initialize {
+  if (self == [Hello class]) {
+    defaultHelloInstance = [[Hello alloc] init];
+  }
+}
++ (Hello*) defaultInstance {
+  return defaultHelloInstance;
+}
+- (Hello*) defaultInstance {
+  return defaultHelloInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasProtocolVersion) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasProtocolVersion) {
+    [output writeEnum:1 value:self.protocolVersion];
+  }
+  if (self.hasUuid) {
+    [output writeString:2 value:self.uuid];
+  }
+  if (self.hasRequireConnectedCamera) {
+    [output writeBool:3 value:self.requireConnectedCamera];
+  }
+  if (self.hasSessionToken) {
+    [output writeString:4 value:self.sessionToken];
+  }
+  if (self.hasIsCamera) {
+    [output writeBool:5 value:self.isCamera];
+  }
+  if (self.hasDeviceId) {
+    [output writeString:6 value:self.deviceId];
+  }
+  if (self.hasUserAgent) {
+    [output writeString:7 value:self.userAgent];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasProtocolVersion) {
+    size_ += computeEnumSize(1, self.protocolVersion);
+  }
+  if (self.hasUuid) {
+    size_ += computeStringSize(2, self.uuid);
+  }
+  if (self.hasRequireConnectedCamera) {
+    size_ += computeBoolSize(3, self.requireConnectedCamera);
+  }
+  if (self.hasSessionToken) {
+    size_ += computeStringSize(4, self.sessionToken);
+  }
+  if (self.hasIsCamera) {
+    size_ += computeBoolSize(5, self.isCamera);
+  }
+  if (self.hasDeviceId) {
+    size_ += computeStringSize(6, self.deviceId);
+  }
+  if (self.hasUserAgent) {
+    size_ += computeStringSize(7, self.userAgent);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Hello*) parseFromData:(NSData*) data {
+  return (Hello*)[[[Hello builder] mergeFromData:data] build];
+}
++ (Hello*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Hello*)[[[Hello builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Hello*) parseFromInputStream:(NSInputStream*) input {
+  return (Hello*)[[[Hello builder] mergeFromInputStream:input] build];
+}
++ (Hello*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Hello*)[[[Hello builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Hello*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Hello*)[[[Hello builder] mergeFromCodedInputStream:input] build];
+}
++ (Hello*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Hello*)[[[Hello builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (HelloBuilder*) builder {
+  return [[HelloBuilder alloc] init];
+}
++ (HelloBuilder*) builderWithPrototype:(Hello*) prototype {
+  return [[Hello builder] mergeFrom:prototype];
+}
+- (HelloBuilder*) builder {
+  return [Hello builder];
+}
+- (HelloBuilder*) toBuilder {
+  return [Hello builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasProtocolVersion) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"protocolVersion", self.protocolVersion];
+  }
+  if (self.hasUuid) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"uuid", self.uuid];
+  }
+  if (self.hasRequireConnectedCamera) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"requireConnectedCamera", [NSNumber numberWithBool:self.requireConnectedCamera]];
+  }
+  if (self.hasSessionToken) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionToken", self.sessionToken];
+  }
+  if (self.hasIsCamera) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"isCamera", [NSNumber numberWithBool:self.isCamera]];
+  }
+  if (self.hasDeviceId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deviceId", self.deviceId];
+  }
+  if (self.hasUserAgent) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"userAgent", self.userAgent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Hello class]]) {
+    return NO;
+  }
+  Hello *otherMessage = other;
+  return
+      self.hasProtocolVersion == otherMessage.hasProtocolVersion &&
+      (!self.hasProtocolVersion || self.protocolVersion == otherMessage.protocolVersion) &&
+      self.hasUuid == otherMessage.hasUuid &&
+      (!self.hasUuid || [self.uuid isEqual:otherMessage.uuid]) &&
+      self.hasRequireConnectedCamera == otherMessage.hasRequireConnectedCamera &&
+      (!self.hasRequireConnectedCamera || self.requireConnectedCamera == otherMessage.requireConnectedCamera) &&
+      self.hasSessionToken == otherMessage.hasSessionToken &&
+      (!self.hasSessionToken || [self.sessionToken isEqual:otherMessage.sessionToken]) &&
+      self.hasIsCamera == otherMessage.hasIsCamera &&
+      (!self.hasIsCamera || self.isCamera == otherMessage.isCamera) &&
+      self.hasDeviceId == otherMessage.hasDeviceId &&
+      (!self.hasDeviceId || [self.deviceId isEqual:otherMessage.deviceId]) &&
+      self.hasUserAgent == otherMessage.hasUserAgent &&
+      (!self.hasUserAgent || [self.userAgent isEqual:otherMessage.userAgent]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasProtocolVersion) {
+    hashCode = hashCode * 31 + self.protocolVersion;
+  }
+  if (self.hasUuid) {
+    hashCode = hashCode * 31 + [self.uuid hash];
+  }
+  if (self.hasRequireConnectedCamera) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.requireConnectedCamera] hash];
+  }
+  if (self.hasSessionToken) {
+    hashCode = hashCode * 31 + [self.sessionToken hash];
+  }
+  if (self.hasIsCamera) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.isCamera] hash];
+  }
+  if (self.hasDeviceId) {
+    hashCode = hashCode * 31 + [self.deviceId hash];
+  }
+  if (self.hasUserAgent) {
+    hashCode = hashCode * 31 + [self.userAgent hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL HelloProtocolVersionIsValidValue(HelloProtocolVersion value) {
+  switch (value) {
+    case HelloProtocolVersionVersion1:
+    case HelloProtocolVersionVersion2:
+    case HelloProtocolVersionVersion3:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface HelloBuilder()
+@property (strong) Hello* result;
+@end
+
+@implementation HelloBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Hello alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (HelloBuilder*) clear {
+  self.result = [[Hello alloc] init];
+  return self;
+}
+- (HelloBuilder*) clone {
+  return [Hello builderWithPrototype:result];
+}
+- (Hello*) defaultInstance {
+  return [Hello defaultInstance];
+}
+- (Hello*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Hello*) buildPartial {
+  Hello* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (HelloBuilder*) mergeFrom:(Hello*) other {
+  if (other == [Hello defaultInstance]) {
+    return self;
+  }
+  if (other.hasProtocolVersion) {
+    [self setProtocolVersion:other.protocolVersion];
+  }
+  if (other.hasUuid) {
+    [self setUuid:other.uuid];
+  }
+  if (other.hasRequireConnectedCamera) {
+    [self setRequireConnectedCamera:other.requireConnectedCamera];
+  }
+  if (other.hasSessionToken) {
+    [self setSessionToken:other.sessionToken];
+  }
+  if (other.hasIsCamera) {
+    [self setIsCamera:other.isCamera];
+  }
+  if (other.hasDeviceId) {
+    [self setDeviceId:other.deviceId];
+  }
+  if (other.hasUserAgent) {
+    [self setUserAgent:other.userAgent];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (HelloBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (HelloBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        HelloProtocolVersion value = (HelloProtocolVersion)[input readEnum];
+        if (HelloProtocolVersionIsValidValue(value)) {
+          [self setProtocolVersion:value];
+        } else {
+          [unknownFields mergeVarintField:1 value:value];
+        }
+        break;
+      }
+      case 18: {
+        [self setUuid:[input readString]];
+        break;
+      }
+      case 24: {
+        [self setRequireConnectedCamera:[input readBool]];
+        break;
+      }
+      case 34: {
+        [self setSessionToken:[input readString]];
+        break;
+      }
+      case 40: {
+        [self setIsCamera:[input readBool]];
+        break;
+      }
+      case 50: {
+        [self setDeviceId:[input readString]];
+        break;
+      }
+      case 58: {
+        [self setUserAgent:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasProtocolVersion {
+  return result.hasProtocolVersion;
+}
+- (HelloProtocolVersion) protocolVersion {
+  return result.protocolVersion;
+}
+- (HelloBuilder*) setProtocolVersion:(HelloProtocolVersion) value {
+  result.hasProtocolVersion = YES;
+  result.protocolVersion = value;
+  return self;
+}
+- (HelloBuilder*) clearProtocolVersion {
+  result.hasProtocolVersion = NO;
+  result.protocolVersion = HelloProtocolVersionVersion1;
+  return self;
+}
+- (BOOL) hasUuid {
+  return result.hasUuid;
+}
+- (NSString*) uuid {
+  return result.uuid;
+}
+- (HelloBuilder*) setUuid:(NSString*) value {
+  result.hasUuid = YES;
+  result.uuid = value;
+  return self;
+}
+- (HelloBuilder*) clearUuid {
+  result.hasUuid = NO;
+  result.uuid = @"";
+  return self;
+}
+- (BOOL) hasRequireConnectedCamera {
+  return result.hasRequireConnectedCamera;
+}
+- (BOOL) requireConnectedCamera {
+  return result.requireConnectedCamera;
+}
+- (HelloBuilder*) setRequireConnectedCamera:(BOOL) value {
+  result.hasRequireConnectedCamera = YES;
+  result.requireConnectedCamera = value;
+  return self;
+}
+- (HelloBuilder*) clearRequireConnectedCamera {
+  result.hasRequireConnectedCamera = NO;
+  result.requireConnectedCamera = NO;
+  return self;
+}
+- (BOOL) hasSessionToken {
+  return result.hasSessionToken;
+}
+- (NSString*) sessionToken {
+  return result.sessionToken;
+}
+- (HelloBuilder*) setSessionToken:(NSString*) value {
+  result.hasSessionToken = YES;
+  result.sessionToken = value;
+  return self;
+}
+- (HelloBuilder*) clearSessionToken {
+  result.hasSessionToken = NO;
+  result.sessionToken = @"";
+  return self;
+}
+- (BOOL) hasIsCamera {
+  return result.hasIsCamera;
+}
+- (BOOL) isCamera {
+  return result.isCamera;
+}
+- (HelloBuilder*) setIsCamera:(BOOL) value {
+  result.hasIsCamera = YES;
+  result.isCamera = value;
+  return self;
+}
+- (HelloBuilder*) clearIsCamera {
+  result.hasIsCamera = NO;
+  result.isCamera = NO;
+  return self;
+}
+- (BOOL) hasDeviceId {
+  return result.hasDeviceId;
+}
+- (NSString*) deviceId {
+  return result.deviceId;
+}
+- (HelloBuilder*) setDeviceId:(NSString*) value {
+  result.hasDeviceId = YES;
+  result.deviceId = value;
+  return self;
+}
+- (HelloBuilder*) clearDeviceId {
+  result.hasDeviceId = NO;
+  result.deviceId = @"";
+  return self;
+}
+- (BOOL) hasUserAgent {
+  return result.hasUserAgent;
+}
+- (NSString*) userAgent {
+  return result.userAgent;
+}
+- (HelloBuilder*) setUserAgent:(NSString*) value {
+  result.hasUserAgent = YES;
+  result.userAgent = value;
+  return self;
+}
+- (HelloBuilder*) clearUserAgent {
+  result.hasUserAgent = NO;
+  result.userAgent = @"";
+  return self;
+}
+@end
+
+@interface Ok ()
+@property UInt32 udpPort;
+@end
+
+@implementation Ok
+
+- (BOOL) hasUdpPort {
+  return !!hasUdpPort_;
+}
+- (void) setHasUdpPort:(BOOL) value_ {
+  hasUdpPort_ = !!value_;
+}
+@synthesize udpPort;
+- (id) init {
+  if ((self = [super init])) {
+    self.udpPort = 0;
+  }
+  return self;
+}
+static Ok* defaultOkInstance = nil;
++ (void) initialize {
+  if (self == [Ok class]) {
+    defaultOkInstance = [[Ok alloc] init];
+  }
+}
++ (Ok*) defaultInstance {
+  return defaultOkInstance;
+}
+- (Ok*) defaultInstance {
+  return defaultOkInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasUdpPort) {
+    [output writeUInt32:1 value:self.udpPort];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasUdpPort) {
+    size_ += computeUInt32Size(1, self.udpPort);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Ok*) parseFromData:(NSData*) data {
+  return (Ok*)[[[Ok builder] mergeFromData:data] build];
+}
++ (Ok*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Ok*)[[[Ok builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Ok*) parseFromInputStream:(NSInputStream*) input {
+  return (Ok*)[[[Ok builder] mergeFromInputStream:input] build];
+}
++ (Ok*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Ok*)[[[Ok builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Ok*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Ok*)[[[Ok builder] mergeFromCodedInputStream:input] build];
+}
++ (Ok*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Ok*)[[[Ok builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (OkBuilder*) builder {
+  return [[OkBuilder alloc] init];
+}
++ (OkBuilder*) builderWithPrototype:(Ok*) prototype {
+  return [[Ok builder] mergeFrom:prototype];
+}
+- (OkBuilder*) builder {
+  return [Ok builder];
+}
+- (OkBuilder*) toBuilder {
+  return [Ok builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasUdpPort) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"udpPort", [NSNumber numberWithInteger:self.udpPort]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Ok class]]) {
+    return NO;
+  }
+  Ok *otherMessage = other;
+  return
+      self.hasUdpPort == otherMessage.hasUdpPort &&
+      (!self.hasUdpPort || self.udpPort == otherMessage.udpPort) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasUdpPort) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.udpPort] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface OkBuilder()
+@property (strong) Ok* result;
+@end
+
+@implementation OkBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Ok alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (OkBuilder*) clear {
+  self.result = [[Ok alloc] init];
+  return self;
+}
+- (OkBuilder*) clone {
+  return [Ok builderWithPrototype:result];
+}
+- (Ok*) defaultInstance {
+  return [Ok defaultInstance];
+}
+- (Ok*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Ok*) buildPartial {
+  Ok* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (OkBuilder*) mergeFrom:(Ok*) other {
+  if (other == [Ok defaultInstance]) {
+    return self;
+  }
+  if (other.hasUdpPort) {
+    [self setUdpPort:other.udpPort];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (OkBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (OkBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setUdpPort:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasUdpPort {
+  return result.hasUdpPort;
+}
+- (UInt32) udpPort {
+  return result.udpPort;
+}
+- (OkBuilder*) setUdpPort:(UInt32) value {
+  result.hasUdpPort = YES;
+  result.udpPort = value;
+  return self;
+}
+- (OkBuilder*) clearUdpPort {
+  result.hasUdpPort = NO;
+  result.udpPort = 0;
+  return self;
+}
+@end
+
+@interface Error ()
+@property ErrorCode code;
+@property (strong) NSString* message;
+@end
+
+@implementation Error
+
+- (BOOL) hasCode {
+  return !!hasCode_;
+}
+- (void) setHasCode:(BOOL) value_ {
+  hasCode_ = !!value_;
+}
+@synthesize code;
+- (BOOL) hasMessage {
+  return !!hasMessage_;
+}
+- (void) setHasMessage:(BOOL) value_ {
+  hasMessage_ = !!value_;
+}
+@synthesize message;
+- (id) init {
+  if ((self = [super init])) {
+    self.code = ErrorCodeErrorCameraNotConnected;
+    self.message = @"";
+  }
+  return self;
+}
+static Error* defaultErrorInstance = nil;
++ (void) initialize {
+  if (self == [Error class]) {
+    defaultErrorInstance = [[Error alloc] init];
+  }
+}
++ (Error*) defaultInstance {
+  return defaultErrorInstance;
+}
+- (Error*) defaultInstance {
+  return defaultErrorInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasCode) {
+    return NO;
+  }
+  if (!self.hasMessage) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasCode) {
+    [output writeEnum:1 value:self.code];
+  }
+  if (self.hasMessage) {
+    [output writeString:2 value:self.message];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasCode) {
+    size_ += computeEnumSize(1, self.code);
+  }
+  if (self.hasMessage) {
+    size_ += computeStringSize(2, self.message);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Error*) parseFromData:(NSData*) data {
+  return (Error*)[[[Error builder] mergeFromData:data] build];
+}
++ (Error*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Error*)[[[Error builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Error*) parseFromInputStream:(NSInputStream*) input {
+  return (Error*)[[[Error builder] mergeFromInputStream:input] build];
+}
++ (Error*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Error*)[[[Error builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Error*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Error*)[[[Error builder] mergeFromCodedInputStream:input] build];
+}
++ (Error*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Error*)[[[Error builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ErrorBuilder*) builder {
+  return [[ErrorBuilder alloc] init];
+}
++ (ErrorBuilder*) builderWithPrototype:(Error*) prototype {
+  return [[Error builder] mergeFrom:prototype];
+}
+- (ErrorBuilder*) builder {
+  return [Error builder];
+}
+- (ErrorBuilder*) toBuilder {
+  return [Error builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasCode) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"code", self.code];
+  }
+  if (self.hasMessage) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"message", self.message];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Error class]]) {
+    return NO;
+  }
+  Error *otherMessage = other;
+  return
+      self.hasCode == otherMessage.hasCode &&
+      (!self.hasCode || self.code == otherMessage.code) &&
+      self.hasMessage == otherMessage.hasMessage &&
+      (!self.hasMessage || [self.message isEqual:otherMessage.message]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasCode) {
+    hashCode = hashCode * 31 + self.code;
+  }
+  if (self.hasMessage) {
+    hashCode = hashCode * 31 + [self.message hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ErrorBuilder()
+@property (strong) Error* result;
+@end
+
+@implementation ErrorBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Error alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ErrorBuilder*) clear {
+  self.result = [[Error alloc] init];
+  return self;
+}
+- (ErrorBuilder*) clone {
+  return [Error builderWithPrototype:result];
+}
+- (Error*) defaultInstance {
+  return [Error defaultInstance];
+}
+- (Error*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Error*) buildPartial {
+  Error* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ErrorBuilder*) mergeFrom:(Error*) other {
+  if (other == [Error defaultInstance]) {
+    return self;
+  }
+  if (other.hasCode) {
+    [self setCode:other.code];
+  }
+  if (other.hasMessage) {
+    [self setMessage:other.message];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ErrorBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ErrorBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        ErrorCode value = (ErrorCode)[input readEnum];
+        if (ErrorCodeIsValidValue(value)) {
+          [self setCode:value];
+        } else {
+          [unknownFields mergeVarintField:1 value:value];
+        }
+        break;
+      }
+      case 18: {
+        [self setMessage:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasCode {
+  return result.hasCode;
+}
+- (ErrorCode) code {
+  return result.code;
+}
+- (ErrorBuilder*) setCode:(ErrorCode) value {
+  result.hasCode = YES;
+  result.code = value;
+  return self;
+}
+- (ErrorBuilder*) clearCode {
+  result.hasCode = NO;
+  result.code = ErrorCodeErrorCameraNotConnected;
+  return self;
+}
+- (BOOL) hasMessage {
+  return result.hasMessage;
+}
+- (NSString*) message {
+  return result.message;
+}
+- (ErrorBuilder*) setMessage:(NSString*) value {
+  result.hasMessage = YES;
+  result.message = value;
+  return self;
+}
+- (ErrorBuilder*) clearMessage {
+  result.hasMessage = NO;
+  result.message = @"";
+  return self;
+}
+@end
+
+@interface PingCamera ()
+@end
+
+@implementation PingCamera
+
+- (id) init {
+  if ((self = [super init])) {
+  }
+  return self;
+}
+static PingCamera* defaultPingCameraInstance = nil;
++ (void) initialize {
+  if (self == [PingCamera class]) {
+    defaultPingCameraInstance = [[PingCamera alloc] init];
+  }
+}
++ (PingCamera*) defaultInstance {
+  return defaultPingCameraInstance;
+}
+- (PingCamera*) defaultInstance {
+  return defaultPingCameraInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PingCamera*) parseFromData:(NSData*) data {
+  return (PingCamera*)[[[PingCamera builder] mergeFromData:data] build];
+}
++ (PingCamera*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PingCamera*)[[[PingCamera builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PingCamera*) parseFromInputStream:(NSInputStream*) input {
+  return (PingCamera*)[[[PingCamera builder] mergeFromInputStream:input] build];
+}
++ (PingCamera*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PingCamera*)[[[PingCamera builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PingCamera*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PingCamera*)[[[PingCamera builder] mergeFromCodedInputStream:input] build];
+}
++ (PingCamera*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PingCamera*)[[[PingCamera builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PingCameraBuilder*) builder {
+  return [[PingCameraBuilder alloc] init];
+}
++ (PingCameraBuilder*) builderWithPrototype:(PingCamera*) prototype {
+  return [[PingCamera builder] mergeFrom:prototype];
+}
+- (PingCameraBuilder*) builder {
+  return [PingCamera builder];
+}
+- (PingCameraBuilder*) toBuilder {
+  return [PingCamera builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PingCamera class]]) {
+    return NO;
+  }
+  PingCamera *otherMessage = other;
+  return
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PingCameraBuilder()
+@property (strong) PingCamera* result;
+@end
+
+@implementation PingCameraBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PingCamera alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PingCameraBuilder*) clear {
+  self.result = [[PingCamera alloc] init];
+  return self;
+}
+- (PingCameraBuilder*) clone {
+  return [PingCamera builderWithPrototype:result];
+}
+- (PingCamera*) defaultInstance {
+  return [PingCamera defaultInstance];
+}
+- (PingCamera*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PingCamera*) buildPartial {
+  PingCamera* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PingCameraBuilder*) mergeFrom:(PingCamera*) other {
+  if (other == [PingCamera defaultInstance]) {
+    return self;
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PingCameraBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PingCameraBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+    }
+  }
+}
+@end
+
+@interface AudioPayload ()
+@property (strong) NSData* payload;
+@property UInt32 sessionId;
+@property CodecType codec;
+@property UInt32 sampleRate;
+@end
+
+@implementation AudioPayload
+
+- (BOOL) hasPayload {
+  return !!hasPayload_;
+}
+- (void) setHasPayload:(BOOL) value_ {
+  hasPayload_ = !!value_;
+}
+@synthesize payload;
+- (BOOL) hasSessionId {
+  return !!hasSessionId_;
+}
+- (void) setHasSessionId:(BOOL) value_ {
+  hasSessionId_ = !!value_;
+}
+@synthesize sessionId;
+- (BOOL) hasCodec {
+  return !!hasCodec_;
+}
+- (void) setHasCodec:(BOOL) value_ {
+  hasCodec_ = !!value_;
+}
+@synthesize codec;
+- (BOOL) hasSampleRate {
+  return !!hasSampleRate_;
+}
+- (void) setHasSampleRate:(BOOL) value_ {
+  hasSampleRate_ = !!value_;
+}
+@synthesize sampleRate;
+- (id) init {
+  if ((self = [super init])) {
+    self.payload = [NSData data];
+    self.sessionId = 0;
+    self.codec = CodecTypeSpeex;
+    self.sampleRate = 0;
+  }
+  return self;
+}
+static AudioPayload* defaultAudioPayloadInstance = nil;
++ (void) initialize {
+  if (self == [AudioPayload class]) {
+    defaultAudioPayloadInstance = [[AudioPayload alloc] init];
+  }
+}
++ (AudioPayload*) defaultInstance {
+  return defaultAudioPayloadInstance;
+}
+- (AudioPayload*) defaultInstance {
+  return defaultAudioPayloadInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasPayload) {
+    return NO;
+  }
+  if (!self.hasSessionId) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasPayload) {
+    [output writeData:1 value:self.payload];
+  }
+  if (self.hasSessionId) {
+    [output writeUInt32:2 value:self.sessionId];
+  }
+  if (self.hasCodec) {
+    [output writeEnum:3 value:self.codec];
+  }
+  if (self.hasSampleRate) {
+    [output writeUInt32:4 value:self.sampleRate];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasPayload) {
+    size_ += computeDataSize(1, self.payload);
+  }
+  if (self.hasSessionId) {
+    size_ += computeUInt32Size(2, self.sessionId);
+  }
+  if (self.hasCodec) {
+    size_ += computeEnumSize(3, self.codec);
+  }
+  if (self.hasSampleRate) {
+    size_ += computeUInt32Size(4, self.sampleRate);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (AudioPayload*) parseFromData:(NSData*) data {
+  return (AudioPayload*)[[[AudioPayload builder] mergeFromData:data] build];
+}
++ (AudioPayload*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AudioPayload*)[[[AudioPayload builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (AudioPayload*) parseFromInputStream:(NSInputStream*) input {
+  return (AudioPayload*)[[[AudioPayload builder] mergeFromInputStream:input] build];
+}
++ (AudioPayload*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AudioPayload*)[[[AudioPayload builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (AudioPayload*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (AudioPayload*)[[[AudioPayload builder] mergeFromCodedInputStream:input] build];
+}
++ (AudioPayload*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (AudioPayload*)[[[AudioPayload builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (AudioPayloadBuilder*) builder {
+  return [[AudioPayloadBuilder alloc] init];
+}
++ (AudioPayloadBuilder*) builderWithPrototype:(AudioPayload*) prototype {
+  return [[AudioPayload builder] mergeFrom:prototype];
+}
+- (AudioPayloadBuilder*) builder {
+  return [AudioPayload builder];
+}
+- (AudioPayloadBuilder*) toBuilder {
+  return [AudioPayload builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasPayload) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"payload", self.payload];
+  }
+  if (self.hasSessionId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionId", [NSNumber numberWithInteger:self.sessionId]];
+  }
+  if (self.hasCodec) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"codec", self.codec];
+  }
+  if (self.hasSampleRate) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sampleRate", [NSNumber numberWithInteger:self.sampleRate]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[AudioPayload class]]) {
+    return NO;
+  }
+  AudioPayload *otherMessage = other;
+  return
+      self.hasPayload == otherMessage.hasPayload &&
+      (!self.hasPayload || [self.payload isEqual:otherMessage.payload]) &&
+      self.hasSessionId == otherMessage.hasSessionId &&
+      (!self.hasSessionId || self.sessionId == otherMessage.sessionId) &&
+      self.hasCodec == otherMessage.hasCodec &&
+      (!self.hasCodec || self.codec == otherMessage.codec) &&
+      self.hasSampleRate == otherMessage.hasSampleRate &&
+      (!self.hasSampleRate || self.sampleRate == otherMessage.sampleRate) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasPayload) {
+    hashCode = hashCode * 31 + [self.payload hash];
+  }
+  if (self.hasSessionId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sessionId] hash];
+  }
+  if (self.hasCodec) {
+    hashCode = hashCode * 31 + self.codec;
+  }
+  if (self.hasSampleRate) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sampleRate] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface AudioPayloadBuilder()
+@property (strong) AudioPayload* result;
+@end
+
+@implementation AudioPayloadBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[AudioPayload alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (AudioPayloadBuilder*) clear {
+  self.result = [[AudioPayload alloc] init];
+  return self;
+}
+- (AudioPayloadBuilder*) clone {
+  return [AudioPayload builderWithPrototype:result];
+}
+- (AudioPayload*) defaultInstance {
+  return [AudioPayload defaultInstance];
+}
+- (AudioPayload*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (AudioPayload*) buildPartial {
+  AudioPayload* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (AudioPayloadBuilder*) mergeFrom:(AudioPayload*) other {
+  if (other == [AudioPayload defaultInstance]) {
+    return self;
+  }
+  if (other.hasPayload) {
+    [self setPayload:other.payload];
+  }
+  if (other.hasSessionId) {
+    [self setSessionId:other.sessionId];
+  }
+  if (other.hasCodec) {
+    [self setCodec:other.codec];
+  }
+  if (other.hasSampleRate) {
+    [self setSampleRate:other.sampleRate];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (AudioPayloadBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (AudioPayloadBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setPayload:[input readData]];
+        break;
+      }
+      case 16: {
+        [self setSessionId:[input readUInt32]];
+        break;
+      }
+      case 24: {
+        CodecType value = (CodecType)[input readEnum];
+        if (CodecTypeIsValidValue(value)) {
+          [self setCodec:value];
+        } else {
+          [unknownFields mergeVarintField:3 value:value];
+        }
+        break;
+      }
+      case 32: {
+        [self setSampleRate:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasPayload {
+  return result.hasPayload;
+}
+- (NSData*) payload {
+  return result.payload;
+}
+- (AudioPayloadBuilder*) setPayload:(NSData*) value {
+  result.hasPayload = YES;
+  result.payload = value;
+  return self;
+}
+- (AudioPayloadBuilder*) clearPayload {
+  result.hasPayload = NO;
+  result.payload = [NSData data];
+  return self;
+}
+- (BOOL) hasSessionId {
+  return result.hasSessionId;
+}
+- (UInt32) sessionId {
+  return result.sessionId;
+}
+- (AudioPayloadBuilder*) setSessionId:(UInt32) value {
+  result.hasSessionId = YES;
+  result.sessionId = value;
+  return self;
+}
+- (AudioPayloadBuilder*) clearSessionId {
+  result.hasSessionId = NO;
+  result.sessionId = 0;
+  return self;
+}
+- (BOOL) hasCodec {
+  return result.hasCodec;
+}
+- (CodecType) codec {
+  return result.codec;
+}
+- (AudioPayloadBuilder*) setCodec:(CodecType) value {
+  result.hasCodec = YES;
+  result.codec = value;
+  return self;
+}
+- (AudioPayloadBuilder*) clearCodec {
+  result.hasCodec = NO;
+  result.codec = CodecTypeSpeex;
+  return self;
+}
+- (BOOL) hasSampleRate {
+  return result.hasSampleRate;
+}
+- (UInt32) sampleRate {
+  return result.sampleRate;
+}
+- (AudioPayloadBuilder*) setSampleRate:(UInt32) value {
+  result.hasSampleRate = YES;
+  result.sampleRate = value;
+  return self;
+}
+- (AudioPayloadBuilder*) clearSampleRate {
+  result.hasSampleRate = NO;
+  result.sampleRate = 0;
+  return self;
+}
+@end
+
+@interface StartPlayback ()
+@property UInt32 sessionId;
+@property CT_AVProfile profile;
+@property Float64 startTime;
+@property (strong) NSData* externalIp;
+@property UInt32 externalPort;
+@property (strong) PBAppendableArray * otherProfilesArray;
+@property StartPlaybackProfileNotFoundAction profileNotFoundAction;
+@end
+
+@implementation StartPlayback
+
+- (BOOL) hasSessionId {
+  return !!hasSessionId_;
+}
+- (void) setHasSessionId:(BOOL) value_ {
+  hasSessionId_ = !!value_;
+}
+@synthesize sessionId;
+- (BOOL) hasProfile {
+  return !!hasProfile_;
+}
+- (void) setHasProfile:(BOOL) value_ {
+  hasProfile_ = !!value_;
+}
+@synthesize profile;
+- (BOOL) hasStartTime {
+  return !!hasStartTime_;
+}
+- (void) setHasStartTime:(BOOL) value_ {
+  hasStartTime_ = !!value_;
+}
+@synthesize startTime;
+- (BOOL) hasExternalIp {
+  return !!hasExternalIp_;
+}
+- (void) setHasExternalIp:(BOOL) value_ {
+  hasExternalIp_ = !!value_;
+}
+@synthesize externalIp;
+- (BOOL) hasExternalPort {
+  return !!hasExternalPort_;
+}
+- (void) setHasExternalPort:(BOOL) value_ {
+  hasExternalPort_ = !!value_;
+}
+@synthesize externalPort;
+@synthesize otherProfilesArray;
+@dynamic otherProfiles;
+- (BOOL) hasProfileNotFoundAction {
+  return !!hasProfileNotFoundAction_;
+}
+- (void) setHasProfileNotFoundAction:(BOOL) value_ {
+  hasProfileNotFoundAction_ = !!value_;
+}
+@synthesize profileNotFoundAction;
+- (id) init {
+  if ((self = [super init])) {
+    self.sessionId = 0;
+    self.profile = CT_AVProfileAudioAac;
+    self.startTime = 0;
+    self.externalIp = [NSData data];
+    self.externalPort = 0;
+    self.profileNotFoundAction = StartPlaybackProfileNotFoundActionRedirect;
+  }
+  return self;
+}
+static StartPlayback* defaultStartPlaybackInstance = nil;
++ (void) initialize {
+  if (self == [StartPlayback class]) {
+    defaultStartPlaybackInstance = [[StartPlayback alloc] init];
+  }
+}
++ (StartPlayback*) defaultInstance {
+  return defaultStartPlaybackInstance;
+}
+- (StartPlayback*) defaultInstance {
+  return defaultStartPlaybackInstance;
+}
+- (PBArray *)otherProfiles {
+  return otherProfilesArray;
+}
+- (CT_AVProfile)otherProfilesAtIndex:(NSUInteger)index {
+  return (CT_AVProfile)[otherProfilesArray enumAtIndex:index];
+}
+- (BOOL) isInitialized {
+  if (!self.hasSessionId) {
+    return NO;
+  }
+  if (!self.hasProfile) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasSessionId) {
+    [output writeUInt32:1 value:self.sessionId];
+  }
+  if (self.hasProfile) {
+    [output writeEnum:2 value:self.profile];
+  }
+  if (self.hasStartTime) {
+    [output writeDouble:3 value:self.startTime];
+  }
+  if (self.hasExternalIp) {
+    [output writeData:4 value:self.externalIp];
+  }
+  if (self.hasExternalPort) {
+    [output writeUInt32:5 value:self.externalPort];
+  }
+  const NSUInteger otherProfilesArrayCount = self.otherProfilesArray.count;
+  const CT_AVProfile *otherProfilesArrayValues = (const CT_AVProfile *)self.otherProfilesArray.data;
+  for (NSUInteger i = 0; i < otherProfilesArrayCount; ++i) {
+    [output writeEnum:6 value:otherProfilesArrayValues[i]];
+  }
+  if (self.hasProfileNotFoundAction) {
+    [output writeEnum:7 value:self.profileNotFoundAction];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasSessionId) {
+    size_ += computeUInt32Size(1, self.sessionId);
+  }
+  if (self.hasProfile) {
+    size_ += computeEnumSize(2, self.profile);
+  }
+  if (self.hasStartTime) {
+    size_ += computeDoubleSize(3, self.startTime);
+  }
+  if (self.hasExternalIp) {
+    size_ += computeDataSize(4, self.externalIp);
+  }
+  if (self.hasExternalPort) {
+    size_ += computeUInt32Size(5, self.externalPort);
+  }
+  {
+    SInt32 dataSize = 0;
+    const NSUInteger count = self.otherProfilesArray.count;
+    const CT_AVProfile *values = (const CT_AVProfile *)self.otherProfilesArray.data;
+    for (NSUInteger i = 0; i < count; ++i) {
+      dataSize += computeEnumSizeNoTag(values[i]);
+    }
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  if (self.hasProfileNotFoundAction) {
+    size_ += computeEnumSize(7, self.profileNotFoundAction);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (StartPlayback*) parseFromData:(NSData*) data {
+  return (StartPlayback*)[[[StartPlayback builder] mergeFromData:data] build];
+}
++ (StartPlayback*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (StartPlayback*)[[[StartPlayback builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (StartPlayback*) parseFromInputStream:(NSInputStream*) input {
+  return (StartPlayback*)[[[StartPlayback builder] mergeFromInputStream:input] build];
+}
++ (StartPlayback*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (StartPlayback*)[[[StartPlayback builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (StartPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (StartPlayback*)[[[StartPlayback builder] mergeFromCodedInputStream:input] build];
+}
++ (StartPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (StartPlayback*)[[[StartPlayback builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (StartPlaybackBuilder*) builder {
+  return [[StartPlaybackBuilder alloc] init];
+}
++ (StartPlaybackBuilder*) builderWithPrototype:(StartPlayback*) prototype {
+  return [[StartPlayback builder] mergeFrom:prototype];
+}
+- (StartPlaybackBuilder*) builder {
+  return [StartPlayback builder];
+}
+- (StartPlaybackBuilder*) toBuilder {
+  return [StartPlayback builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasSessionId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionId", [NSNumber numberWithInteger:self.sessionId]];
+  }
+  if (self.hasProfile) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"profile", self.profile];
+  }
+  if (self.hasStartTime) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"startTime", [NSNumber numberWithDouble:self.startTime]];
+  }
+  if (self.hasExternalIp) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"externalIp", self.externalIp];
+  }
+  if (self.hasExternalPort) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"externalPort", [NSNumber numberWithInteger:self.externalPort]];
+  }
+  [self.otherProfilesArray enumerateObjectsUsingBlock:^(id element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"otherProfiles", element];
+  }];
+  if (self.hasProfileNotFoundAction) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"profileNotFoundAction", self.profileNotFoundAction];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[StartPlayback class]]) {
+    return NO;
+  }
+  StartPlayback *otherMessage = other;
+  return
+      self.hasSessionId == otherMessage.hasSessionId &&
+      (!self.hasSessionId || self.sessionId == otherMessage.sessionId) &&
+      self.hasProfile == otherMessage.hasProfile &&
+      (!self.hasProfile || self.profile == otherMessage.profile) &&
+      self.hasStartTime == otherMessage.hasStartTime &&
+      (!self.hasStartTime || self.startTime == otherMessage.startTime) &&
+      self.hasExternalIp == otherMessage.hasExternalIp &&
+      (!self.hasExternalIp || [self.externalIp isEqual:otherMessage.externalIp]) &&
+      self.hasExternalPort == otherMessage.hasExternalPort &&
+      (!self.hasExternalPort || self.externalPort == otherMessage.externalPort) &&
+      [self.otherProfilesArray isEqualToArray:otherMessage.otherProfilesArray] &&
+      self.hasProfileNotFoundAction == otherMessage.hasProfileNotFoundAction &&
+      (!self.hasProfileNotFoundAction || self.profileNotFoundAction == otherMessage.profileNotFoundAction) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasSessionId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sessionId] hash];
+  }
+  if (self.hasProfile) {
+    hashCode = hashCode * 31 + self.profile;
+  }
+  if (self.hasStartTime) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithDouble:self.startTime] hash];
+  }
+  if (self.hasExternalIp) {
+    hashCode = hashCode * 31 + [self.externalIp hash];
+  }
+  if (self.hasExternalPort) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.externalPort] hash];
+  }
+  [self.otherProfilesArray enumerateObjectsUsingBlock:^(NSNumber* element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + element.longValue;
+  }];
+  if (self.hasProfileNotFoundAction) {
+    hashCode = hashCode * 31 + self.profileNotFoundAction;
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL StartPlaybackProfileNotFoundActionIsValidValue(StartPlaybackProfileNotFoundAction value) {
+  switch (value) {
+    case StartPlaybackProfileNotFoundActionRedirect:
+    case StartPlaybackProfileNotFoundActionUseNextAvailable:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface StartPlaybackBuilder()
+@property (strong) StartPlayback* result;
+@end
+
+@implementation StartPlaybackBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[StartPlayback alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (StartPlaybackBuilder*) clear {
+  self.result = [[StartPlayback alloc] init];
+  return self;
+}
+- (StartPlaybackBuilder*) clone {
+  return [StartPlayback builderWithPrototype:result];
+}
+- (StartPlayback*) defaultInstance {
+  return [StartPlayback defaultInstance];
+}
+- (StartPlayback*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (StartPlayback*) buildPartial {
+  StartPlayback* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (StartPlaybackBuilder*) mergeFrom:(StartPlayback*) other {
+  if (other == [StartPlayback defaultInstance]) {
+    return self;
+  }
+  if (other.hasSessionId) {
+    [self setSessionId:other.sessionId];
+  }
+  if (other.hasProfile) {
+    [self setProfile:other.profile];
+  }
+  if (other.hasStartTime) {
+    [self setStartTime:other.startTime];
+  }
+  if (other.hasExternalIp) {
+    [self setExternalIp:other.externalIp];
+  }
+  if (other.hasExternalPort) {
+    [self setExternalPort:other.externalPort];
+  }
+  if (other.otherProfilesArray.count > 0) {
+    if (result.otherProfilesArray == nil) {
+      result.otherProfilesArray = [other.otherProfilesArray copy];
+    } else {
+      [result.otherProfilesArray appendArray:other.otherProfilesArray];
+    }
+  }
+  if (other.hasProfileNotFoundAction) {
+    [self setProfileNotFoundAction:other.profileNotFoundAction];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (StartPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (StartPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setSessionId:[input readUInt32]];
+        break;
+      }
+      case 16: {
+        CT_AVProfile value = (CT_AVProfile)[input readEnum];
+        if (CT_AVProfileIsValidValue(value)) {
+          [self setProfile:value];
+        } else {
+          [unknownFields mergeVarintField:2 value:value];
+        }
+        break;
+      }
+      case 25: {
+        [self setStartTime:[input readDouble]];
+        break;
+      }
+      case 34: {
+        [self setExternalIp:[input readData]];
+        break;
+      }
+      case 40: {
+        [self setExternalPort:[input readUInt32]];
+        break;
+      }
+      case 48: {
+        CT_AVProfile value = (CT_AVProfile)[input readEnum];
+        if (CT_AVProfileIsValidValue(value)) {
+          [self addOtherProfiles:value];
+        } else {
+          [unknownFields mergeVarintField:6 value:value];
+        }
+        break;
+      }
+      case 56: {
+        StartPlaybackProfileNotFoundAction value = (StartPlaybackProfileNotFoundAction)[input readEnum];
+        if (StartPlaybackProfileNotFoundActionIsValidValue(value)) {
+          [self setProfileNotFoundAction:value];
+        } else {
+          [unknownFields mergeVarintField:7 value:value];
+        }
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasSessionId {
+  return result.hasSessionId;
+}
+- (UInt32) sessionId {
+  return result.sessionId;
+}
+- (StartPlaybackBuilder*) setSessionId:(UInt32) value {
+  result.hasSessionId = YES;
+  result.sessionId = value;
+  return self;
+}
+- (StartPlaybackBuilder*) clearSessionId {
+  result.hasSessionId = NO;
+  result.sessionId = 0;
+  return self;
+}
+- (BOOL) hasProfile {
+  return result.hasProfile;
+}
+- (CT_AVProfile) profile {
+  return result.profile;
+}
+- (StartPlaybackBuilder*) setProfile:(CT_AVProfile) value {
+  result.hasProfile = YES;
+  result.profile = value;
+  return self;
+}
+- (StartPlaybackBuilder*) clearProfile {
+  result.hasProfile = NO;
+  result.profile = CT_AVProfileAudioAac;
+  return self;
+}
+- (BOOL) hasStartTime {
+  return result.hasStartTime;
+}
+- (Float64) startTime {
+  return result.startTime;
+}
+- (StartPlaybackBuilder*) setStartTime:(Float64) value {
+  result.hasStartTime = YES;
+  result.startTime = value;
+  return self;
+}
+- (StartPlaybackBuilder*) clearStartTime {
+  result.hasStartTime = NO;
+  result.startTime = 0;
+  return self;
+}
+- (BOOL) hasExternalIp {
+  return result.hasExternalIp;
+}
+- (NSData*) externalIp {
+  return result.externalIp;
+}
+- (StartPlaybackBuilder*) setExternalIp:(NSData*) value {
+  result.hasExternalIp = YES;
+  result.externalIp = value;
+  return self;
+}
+- (StartPlaybackBuilder*) clearExternalIp {
+  result.hasExternalIp = NO;
+  result.externalIp = [NSData data];
+  return self;
+}
+- (BOOL) hasExternalPort {
+  return result.hasExternalPort;
+}
+- (UInt32) externalPort {
+  return result.externalPort;
+}
+- (StartPlaybackBuilder*) setExternalPort:(UInt32) value {
+  result.hasExternalPort = YES;
+  result.externalPort = value;
+  return self;
+}
+- (StartPlaybackBuilder*) clearExternalPort {
+  result.hasExternalPort = NO;
+  result.externalPort = 0;
+  return self;
+}
+- (PBAppendableArray *)otherProfiles {
+  return result.otherProfilesArray;
+}
+- (CT_AVProfile)otherProfilesAtIndex:(NSUInteger)index {
+  return [result otherProfilesAtIndex:index];
+}
+- (StartPlaybackBuilder *)addOtherProfiles:(CT_AVProfile)value {
+  if (result.otherProfilesArray == nil) {
+    result.otherProfilesArray = [PBAppendableArray arrayWithValueType:PBArrayValueTypeInt32];
+  }
+  [result.otherProfilesArray addEnum:value];
+  return self;
+}
+- (StartPlaybackBuilder *)setOtherProfilesArray:(NSArray *)array {
+  result.otherProfilesArray = [PBAppendableArray arrayWithArray:array valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (StartPlaybackBuilder *)setOtherProfilesValues:(const CT_AVProfile *)values count:(NSUInteger)count {
+  result.otherProfilesArray = [PBAppendableArray arrayWithValues:values count:count valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (StartPlaybackBuilder *)clearOtherProfiles {
+  result.otherProfilesArray = nil;
+  return self;
+}
+- (BOOL) hasProfileNotFoundAction {
+  return result.hasProfileNotFoundAction;
+}
+- (StartPlaybackProfileNotFoundAction) profileNotFoundAction {
+  return result.profileNotFoundAction;
+}
+- (StartPlaybackBuilder*) setProfileNotFoundAction:(StartPlaybackProfileNotFoundAction) value {
+  result.hasProfileNotFoundAction = YES;
+  result.profileNotFoundAction = value;
+  return self;
+}
+- (StartPlaybackBuilder*) clearProfileNotFoundAction {
+  result.hasProfileNotFoundAction = NO;
+  result.profileNotFoundAction = StartPlaybackProfileNotFoundActionRedirect;
+  return self;
+}
+@end
+
+@interface StopPlayback ()
+@property UInt32 sessionId;
+@end
+
+@implementation StopPlayback
+
+- (BOOL) hasSessionId {
+  return !!hasSessionId_;
+}
+- (void) setHasSessionId:(BOOL) value_ {
+  hasSessionId_ = !!value_;
+}
+@synthesize sessionId;
+- (id) init {
+  if ((self = [super init])) {
+    self.sessionId = 0;
+  }
+  return self;
+}
+static StopPlayback* defaultStopPlaybackInstance = nil;
++ (void) initialize {
+  if (self == [StopPlayback class]) {
+    defaultStopPlaybackInstance = [[StopPlayback alloc] init];
+  }
+}
++ (StopPlayback*) defaultInstance {
+  return defaultStopPlaybackInstance;
+}
+- (StopPlayback*) defaultInstance {
+  return defaultStopPlaybackInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasSessionId) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasSessionId) {
+    [output writeUInt32:1 value:self.sessionId];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasSessionId) {
+    size_ += computeUInt32Size(1, self.sessionId);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (StopPlayback*) parseFromData:(NSData*) data {
+  return (StopPlayback*)[[[StopPlayback builder] mergeFromData:data] build];
+}
++ (StopPlayback*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (StopPlayback*)[[[StopPlayback builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (StopPlayback*) parseFromInputStream:(NSInputStream*) input {
+  return (StopPlayback*)[[[StopPlayback builder] mergeFromInputStream:input] build];
+}
++ (StopPlayback*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (StopPlayback*)[[[StopPlayback builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (StopPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (StopPlayback*)[[[StopPlayback builder] mergeFromCodedInputStream:input] build];
+}
++ (StopPlayback*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (StopPlayback*)[[[StopPlayback builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (StopPlaybackBuilder*) builder {
+  return [[StopPlaybackBuilder alloc] init];
+}
++ (StopPlaybackBuilder*) builderWithPrototype:(StopPlayback*) prototype {
+  return [[StopPlayback builder] mergeFrom:prototype];
+}
+- (StopPlaybackBuilder*) builder {
+  return [StopPlayback builder];
+}
+- (StopPlaybackBuilder*) toBuilder {
+  return [StopPlayback builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasSessionId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionId", [NSNumber numberWithInteger:self.sessionId]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[StopPlayback class]]) {
+    return NO;
+  }
+  StopPlayback *otherMessage = other;
+  return
+      self.hasSessionId == otherMessage.hasSessionId &&
+      (!self.hasSessionId || self.sessionId == otherMessage.sessionId) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasSessionId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sessionId] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface StopPlaybackBuilder()
+@property (strong) StopPlayback* result;
+@end
+
+@implementation StopPlaybackBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[StopPlayback alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (StopPlaybackBuilder*) clear {
+  self.result = [[StopPlayback alloc] init];
+  return self;
+}
+- (StopPlaybackBuilder*) clone {
+  return [StopPlayback builderWithPrototype:result];
+}
+- (StopPlayback*) defaultInstance {
+  return [StopPlayback defaultInstance];
+}
+- (StopPlayback*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (StopPlayback*) buildPartial {
+  StopPlayback* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (StopPlaybackBuilder*) mergeFrom:(StopPlayback*) other {
+  if (other == [StopPlayback defaultInstance]) {
+    return self;
+  }
+  if (other.hasSessionId) {
+    [self setSessionId:other.sessionId];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (StopPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (StopPlaybackBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setSessionId:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasSessionId {
+  return result.hasSessionId;
+}
+- (UInt32) sessionId {
+  return result.sessionId;
+}
+- (StopPlaybackBuilder*) setSessionId:(UInt32) value {
+  result.hasSessionId = YES;
+  result.sessionId = value;
+  return self;
+}
+- (StopPlaybackBuilder*) clearSessionId {
+  result.hasSessionId = NO;
+  result.sessionId = 0;
+  return self;
+}
+@end
+
+@interface PlaybackBegin ()
+@property UInt32 sessionId;
+@property (strong) NSMutableArray * channelsArray;
+@property (strong) NSData* srtpMasterKey;
+@property (strong) NSData* srtpMasterSalt;
+@property UInt32 fecKVal;
+@property UInt32 fecNVal;
+@end
+
+@implementation PlaybackBegin
+
+- (BOOL) hasSessionId {
+  return !!hasSessionId_;
+}
+- (void) setHasSessionId:(BOOL) value_ {
+  hasSessionId_ = !!value_;
+}
+@synthesize sessionId;
+@synthesize channelsArray;
+@dynamic channels;
+- (BOOL) hasSrtpMasterKey {
+  return !!hasSrtpMasterKey_;
+}
+- (void) setHasSrtpMasterKey:(BOOL) value_ {
+  hasSrtpMasterKey_ = !!value_;
+}
+@synthesize srtpMasterKey;
+- (BOOL) hasSrtpMasterSalt {
+  return !!hasSrtpMasterSalt_;
+}
+- (void) setHasSrtpMasterSalt:(BOOL) value_ {
+  hasSrtpMasterSalt_ = !!value_;
+}
+@synthesize srtpMasterSalt;
+- (BOOL) hasFecKVal {
+  return !!hasFecKVal_;
+}
+- (void) setHasFecKVal:(BOOL) value_ {
+  hasFecKVal_ = !!value_;
+}
+@synthesize fecKVal;
+- (BOOL) hasFecNVal {
+  return !!hasFecNVal_;
+}
+- (void) setHasFecNVal:(BOOL) value_ {
+  hasFecNVal_ = !!value_;
+}
+@synthesize fecNVal;
+- (id) init {
+  if ((self = [super init])) {
+    self.sessionId = 0;
+    self.srtpMasterKey = [NSData data];
+    self.srtpMasterSalt = [NSData data];
+    self.fecKVal = 0;
+    self.fecNVal = 0;
+  }
+  return self;
+}
+static PlaybackBegin* defaultPlaybackBeginInstance = nil;
++ (void) initialize {
+  if (self == [PlaybackBegin class]) {
+    defaultPlaybackBeginInstance = [[PlaybackBegin alloc] init];
+  }
+}
++ (PlaybackBegin*) defaultInstance {
+  return defaultPlaybackBeginInstance;
+}
+- (PlaybackBegin*) defaultInstance {
+  return defaultPlaybackBeginInstance;
+}
+- (NSArray *)channels {
+  return channelsArray;
+}
+- (PlaybackBeginStream*)channelsAtIndex:(NSUInteger)index {
+  return [channelsArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  if (!self.hasSessionId) {
+    return NO;
+  }
+  __block BOOL isInitchannels = YES;
+   [self.channels enumerateObjectsUsingBlock:^(PlaybackBeginStream *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitchannels = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitchannels) return isInitchannels;
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasSessionId) {
+    [output writeUInt32:1 value:self.sessionId];
+  }
+  [self.channelsArray enumerateObjectsUsingBlock:^(PlaybackBeginStream *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:2 value:element];
+  }];
+  if (self.hasSrtpMasterKey) {
+    [output writeData:3 value:self.srtpMasterKey];
+  }
+  if (self.hasSrtpMasterSalt) {
+    [output writeData:4 value:self.srtpMasterSalt];
+  }
+  if (self.hasFecKVal) {
+    [output writeUInt32:5 value:self.fecKVal];
+  }
+  if (self.hasFecNVal) {
+    [output writeUInt32:6 value:self.fecNVal];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasSessionId) {
+    size_ += computeUInt32Size(1, self.sessionId);
+  }
+  [self.channelsArray enumerateObjectsUsingBlock:^(PlaybackBeginStream *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(2, element);
+  }];
+  if (self.hasSrtpMasterKey) {
+    size_ += computeDataSize(3, self.srtpMasterKey);
+  }
+  if (self.hasSrtpMasterSalt) {
+    size_ += computeDataSize(4, self.srtpMasterSalt);
+  }
+  if (self.hasFecKVal) {
+    size_ += computeUInt32Size(5, self.fecKVal);
+  }
+  if (self.hasFecNVal) {
+    size_ += computeUInt32Size(6, self.fecNVal);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PlaybackBegin*) parseFromData:(NSData*) data {
+  return (PlaybackBegin*)[[[PlaybackBegin builder] mergeFromData:data] build];
+}
++ (PlaybackBegin*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackBegin*)[[[PlaybackBegin builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackBegin*) parseFromInputStream:(NSInputStream*) input {
+  return (PlaybackBegin*)[[[PlaybackBegin builder] mergeFromInputStream:input] build];
+}
++ (PlaybackBegin*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackBegin*)[[[PlaybackBegin builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PlaybackBegin*)[[[PlaybackBegin builder] mergeFromCodedInputStream:input] build];
+}
++ (PlaybackBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackBegin*)[[[PlaybackBegin builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackBeginBuilder*) builder {
+  return [[PlaybackBeginBuilder alloc] init];
+}
++ (PlaybackBeginBuilder*) builderWithPrototype:(PlaybackBegin*) prototype {
+  return [[PlaybackBegin builder] mergeFrom:prototype];
+}
+- (PlaybackBeginBuilder*) builder {
+  return [PlaybackBegin builder];
+}
+- (PlaybackBeginBuilder*) toBuilder {
+  return [PlaybackBegin builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasSessionId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionId", [NSNumber numberWithInteger:self.sessionId]];
+  }
+  [self.channelsArray enumerateObjectsUsingBlock:^(PlaybackBeginStream *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"channels"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasSrtpMasterKey) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"srtpMasterKey", self.srtpMasterKey];
+  }
+  if (self.hasSrtpMasterSalt) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"srtpMasterSalt", self.srtpMasterSalt];
+  }
+  if (self.hasFecKVal) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"fecKVal", [NSNumber numberWithInteger:self.fecKVal]];
+  }
+  if (self.hasFecNVal) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"fecNVal", [NSNumber numberWithInteger:self.fecNVal]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PlaybackBegin class]]) {
+    return NO;
+  }
+  PlaybackBegin *otherMessage = other;
+  return
+      self.hasSessionId == otherMessage.hasSessionId &&
+      (!self.hasSessionId || self.sessionId == otherMessage.sessionId) &&
+      [self.channelsArray isEqualToArray:otherMessage.channelsArray] &&
+      self.hasSrtpMasterKey == otherMessage.hasSrtpMasterKey &&
+      (!self.hasSrtpMasterKey || [self.srtpMasterKey isEqual:otherMessage.srtpMasterKey]) &&
+      self.hasSrtpMasterSalt == otherMessage.hasSrtpMasterSalt &&
+      (!self.hasSrtpMasterSalt || [self.srtpMasterSalt isEqual:otherMessage.srtpMasterSalt]) &&
+      self.hasFecKVal == otherMessage.hasFecKVal &&
+      (!self.hasFecKVal || self.fecKVal == otherMessage.fecKVal) &&
+      self.hasFecNVal == otherMessage.hasFecNVal &&
+      (!self.hasFecNVal || self.fecNVal == otherMessage.fecNVal) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasSessionId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sessionId] hash];
+  }
+  [self.channelsArray enumerateObjectsUsingBlock:^(PlaybackBeginStream *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasSrtpMasterKey) {
+    hashCode = hashCode * 31 + [self.srtpMasterKey hash];
+  }
+  if (self.hasSrtpMasterSalt) {
+    hashCode = hashCode * 31 + [self.srtpMasterSalt hash];
+  }
+  if (self.hasFecKVal) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.fecKVal] hash];
+  }
+  if (self.hasFecNVal) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.fecNVal] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PlaybackBeginStream ()
+@property UInt32 channelId;
+@property CodecType codecType;
+@property UInt32 sampleRate;
+@property (strong) NSMutableArray * privateDataArray;
+@property Float64 startTime;
+@property UInt32 udpSsrc;
+@property UInt32 rtpStartTime;
+@property CT_AVProfile profile;
+@end
+
+@implementation PlaybackBeginStream
+
+- (BOOL) hasChannelId {
+  return !!hasChannelId_;
+}
+- (void) setHasChannelId:(BOOL) value_ {
+  hasChannelId_ = !!value_;
+}
+@synthesize channelId;
+- (BOOL) hasCodecType {
+  return !!hasCodecType_;
+}
+- (void) setHasCodecType:(BOOL) value_ {
+  hasCodecType_ = !!value_;
+}
+@synthesize codecType;
+- (BOOL) hasSampleRate {
+  return !!hasSampleRate_;
+}
+- (void) setHasSampleRate:(BOOL) value_ {
+  hasSampleRate_ = !!value_;
+}
+@synthesize sampleRate;
+@synthesize privateDataArray;
+@dynamic privateData;
+- (BOOL) hasStartTime {
+  return !!hasStartTime_;
+}
+- (void) setHasStartTime:(BOOL) value_ {
+  hasStartTime_ = !!value_;
+}
+@synthesize startTime;
+- (BOOL) hasUdpSsrc {
+  return !!hasUdpSsrc_;
+}
+- (void) setHasUdpSsrc:(BOOL) value_ {
+  hasUdpSsrc_ = !!value_;
+}
+@synthesize udpSsrc;
+- (BOOL) hasRtpStartTime {
+  return !!hasRtpStartTime_;
+}
+- (void) setHasRtpStartTime:(BOOL) value_ {
+  hasRtpStartTime_ = !!value_;
+}
+@synthesize rtpStartTime;
+- (BOOL) hasProfile {
+  return !!hasProfile_;
+}
+- (void) setHasProfile:(BOOL) value_ {
+  hasProfile_ = !!value_;
+}
+@synthesize profile;
+- (id) init {
+  if ((self = [super init])) {
+    self.channelId = 0;
+    self.codecType = CodecTypeSpeex;
+    self.sampleRate = 0;
+    self.startTime = 0;
+    self.udpSsrc = 0;
+    self.rtpStartTime = 0;
+    self.profile = CT_AVProfileAudioAac;
+  }
+  return self;
+}
+static PlaybackBeginStream* defaultPlaybackBeginStreamInstance = nil;
++ (void) initialize {
+  if (self == [PlaybackBeginStream class]) {
+    defaultPlaybackBeginStreamInstance = [[PlaybackBeginStream alloc] init];
+  }
+}
++ (PlaybackBeginStream*) defaultInstance {
+  return defaultPlaybackBeginStreamInstance;
+}
+- (PlaybackBeginStream*) defaultInstance {
+  return defaultPlaybackBeginStreamInstance;
+}
+- (NSArray *)privateData {
+  return privateDataArray;
+}
+- (NSData*)privateDataAtIndex:(NSUInteger)index {
+  return [privateDataArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  if (!self.hasChannelId) {
+    return NO;
+  }
+  if (!self.hasCodecType) {
+    return NO;
+  }
+  if (!self.hasSampleRate) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasChannelId) {
+    [output writeUInt32:1 value:self.channelId];
+  }
+  if (self.hasCodecType) {
+    [output writeEnum:2 value:self.codecType];
+  }
+  if (self.hasSampleRate) {
+    [output writeUInt32:3 value:self.sampleRate];
+  }
+  [self.privateDataArray enumerateObjectsUsingBlock:^(NSData *element, NSUInteger idx, BOOL *stop) {
+    [output writeData:4 value:element];
+  }];
+  if (self.hasStartTime) {
+    [output writeDouble:5 value:self.startTime];
+  }
+  if (self.hasUdpSsrc) {
+    [output writeUInt32:6 value:self.udpSsrc];
+  }
+  if (self.hasRtpStartTime) {
+    [output writeUInt32:7 value:self.rtpStartTime];
+  }
+  if (self.hasProfile) {
+    [output writeEnum:8 value:self.profile];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasChannelId) {
+    size_ += computeUInt32Size(1, self.channelId);
+  }
+  if (self.hasCodecType) {
+    size_ += computeEnumSize(2, self.codecType);
+  }
+  if (self.hasSampleRate) {
+    size_ += computeUInt32Size(3, self.sampleRate);
+  }
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.privateDataArray.count;
+    [self.privateDataArray enumerateObjectsUsingBlock:^(NSData *element, NSUInteger idx, BOOL *stop) {
+      dataSize += computeDataSizeNoTag(element);
+    }];
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  if (self.hasStartTime) {
+    size_ += computeDoubleSize(5, self.startTime);
+  }
+  if (self.hasUdpSsrc) {
+    size_ += computeUInt32Size(6, self.udpSsrc);
+  }
+  if (self.hasRtpStartTime) {
+    size_ += computeUInt32Size(7, self.rtpStartTime);
+  }
+  if (self.hasProfile) {
+    size_ += computeEnumSize(8, self.profile);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PlaybackBeginStream*) parseFromData:(NSData*) data {
+  return (PlaybackBeginStream*)[[[PlaybackBeginStream builder] mergeFromData:data] build];
+}
++ (PlaybackBeginStream*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackBeginStream*)[[[PlaybackBeginStream builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackBeginStream*) parseFromInputStream:(NSInputStream*) input {
+  return (PlaybackBeginStream*)[[[PlaybackBeginStream builder] mergeFromInputStream:input] build];
+}
++ (PlaybackBeginStream*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackBeginStream*)[[[PlaybackBeginStream builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackBeginStream*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PlaybackBeginStream*)[[[PlaybackBeginStream builder] mergeFromCodedInputStream:input] build];
+}
++ (PlaybackBeginStream*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackBeginStream*)[[[PlaybackBeginStream builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackBeginStreamBuilder*) builder {
+  return [[PlaybackBeginStreamBuilder alloc] init];
+}
++ (PlaybackBeginStreamBuilder*) builderWithPrototype:(PlaybackBeginStream*) prototype {
+  return [[PlaybackBeginStream builder] mergeFrom:prototype];
+}
+- (PlaybackBeginStreamBuilder*) builder {
+  return [PlaybackBeginStream builder];
+}
+- (PlaybackBeginStreamBuilder*) toBuilder {
+  return [PlaybackBeginStream builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasChannelId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"channelId", [NSNumber numberWithInteger:self.channelId]];
+  }
+  if (self.hasCodecType) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"codecType", self.codecType];
+  }
+  if (self.hasSampleRate) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sampleRate", [NSNumber numberWithInteger:self.sampleRate]];
+  }
+  [self.privateDataArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"privateData", obj];
+  }];
+  if (self.hasStartTime) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"startTime", [NSNumber numberWithDouble:self.startTime]];
+  }
+  if (self.hasUdpSsrc) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"udpSsrc", [NSNumber numberWithInteger:self.udpSsrc]];
+  }
+  if (self.hasRtpStartTime) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"rtpStartTime", [NSNumber numberWithInteger:self.rtpStartTime]];
+  }
+  if (self.hasProfile) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"profile", self.profile];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PlaybackBeginStream class]]) {
+    return NO;
+  }
+  PlaybackBeginStream *otherMessage = other;
+  return
+      self.hasChannelId == otherMessage.hasChannelId &&
+      (!self.hasChannelId || self.channelId == otherMessage.channelId) &&
+      self.hasCodecType == otherMessage.hasCodecType &&
+      (!self.hasCodecType || self.codecType == otherMessage.codecType) &&
+      self.hasSampleRate == otherMessage.hasSampleRate &&
+      (!self.hasSampleRate || self.sampleRate == otherMessage.sampleRate) &&
+      [self.privateDataArray isEqualToArray:otherMessage.privateDataArray] &&
+      self.hasStartTime == otherMessage.hasStartTime &&
+      (!self.hasStartTime || self.startTime == otherMessage.startTime) &&
+      self.hasUdpSsrc == otherMessage.hasUdpSsrc &&
+      (!self.hasUdpSsrc || self.udpSsrc == otherMessage.udpSsrc) &&
+      self.hasRtpStartTime == otherMessage.hasRtpStartTime &&
+      (!self.hasRtpStartTime || self.rtpStartTime == otherMessage.rtpStartTime) &&
+      self.hasProfile == otherMessage.hasProfile &&
+      (!self.hasProfile || self.profile == otherMessage.profile) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasChannelId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.channelId] hash];
+  }
+  if (self.hasCodecType) {
+    hashCode = hashCode * 31 + self.codecType;
+  }
+  if (self.hasSampleRate) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sampleRate] hash];
+  }
+  [self.privateDataArray enumerateObjectsUsingBlock:^(id element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasStartTime) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithDouble:self.startTime] hash];
+  }
+  if (self.hasUdpSsrc) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.udpSsrc] hash];
+  }
+  if (self.hasRtpStartTime) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.rtpStartTime] hash];
+  }
+  if (self.hasProfile) {
+    hashCode = hashCode * 31 + self.profile;
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PlaybackBeginStreamBuilder()
+@property (strong) PlaybackBeginStream* result;
+@end
+
+@implementation PlaybackBeginStreamBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PlaybackBeginStream alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PlaybackBeginStreamBuilder*) clear {
+  self.result = [[PlaybackBeginStream alloc] init];
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clone {
+  return [PlaybackBeginStream builderWithPrototype:result];
+}
+- (PlaybackBeginStream*) defaultInstance {
+  return [PlaybackBeginStream defaultInstance];
+}
+- (PlaybackBeginStream*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PlaybackBeginStream*) buildPartial {
+  PlaybackBeginStream* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PlaybackBeginStreamBuilder*) mergeFrom:(PlaybackBeginStream*) other {
+  if (other == [PlaybackBeginStream defaultInstance]) {
+    return self;
+  }
+  if (other.hasChannelId) {
+    [self setChannelId:other.channelId];
+  }
+  if (other.hasCodecType) {
+    [self setCodecType:other.codecType];
+  }
+  if (other.hasSampleRate) {
+    [self setSampleRate:other.sampleRate];
+  }
+  if (other.privateDataArray.count > 0) {
+    if (result.privateDataArray == nil) {
+      result.privateDataArray = [[NSMutableArray alloc] initWithArray:other.privateDataArray];
+    } else {
+      [result.privateDataArray addObjectsFromArray:other.privateDataArray];
+    }
+  }
+  if (other.hasStartTime) {
+    [self setStartTime:other.startTime];
+  }
+  if (other.hasUdpSsrc) {
+    [self setUdpSsrc:other.udpSsrc];
+  }
+  if (other.hasRtpStartTime) {
+    [self setRtpStartTime:other.rtpStartTime];
+  }
+  if (other.hasProfile) {
+    [self setProfile:other.profile];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PlaybackBeginStreamBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setChannelId:[input readUInt32]];
+        break;
+      }
+      case 16: {
+        CodecType value = (CodecType)[input readEnum];
+        if (CodecTypeIsValidValue(value)) {
+          [self setCodecType:value];
+        } else {
+          [unknownFields mergeVarintField:2 value:value];
+        }
+        break;
+      }
+      case 24: {
+        [self setSampleRate:[input readUInt32]];
+        break;
+      }
+      case 34: {
+        [self addPrivateData:[input readData]];
+        break;
+      }
+      case 41: {
+        [self setStartTime:[input readDouble]];
+        break;
+      }
+      case 48: {
+        [self setUdpSsrc:[input readUInt32]];
+        break;
+      }
+      case 56: {
+        [self setRtpStartTime:[input readUInt32]];
+        break;
+      }
+      case 64: {
+        CT_AVProfile value = (CT_AVProfile)[input readEnum];
+        if (CT_AVProfileIsValidValue(value)) {
+          [self setProfile:value];
+        } else {
+          [unknownFields mergeVarintField:8 value:value];
+        }
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasChannelId {
+  return result.hasChannelId;
+}
+- (UInt32) channelId {
+  return result.channelId;
+}
+- (PlaybackBeginStreamBuilder*) setChannelId:(UInt32) value {
+  result.hasChannelId = YES;
+  result.channelId = value;
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clearChannelId {
+  result.hasChannelId = NO;
+  result.channelId = 0;
+  return self;
+}
+- (BOOL) hasCodecType {
+  return result.hasCodecType;
+}
+- (CodecType) codecType {
+  return result.codecType;
+}
+- (PlaybackBeginStreamBuilder*) setCodecType:(CodecType) value {
+  result.hasCodecType = YES;
+  result.codecType = value;
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clearCodecType {
+  result.hasCodecType = NO;
+  result.codecType = CodecTypeSpeex;
+  return self;
+}
+- (BOOL) hasSampleRate {
+  return result.hasSampleRate;
+}
+- (UInt32) sampleRate {
+  return result.sampleRate;
+}
+- (PlaybackBeginStreamBuilder*) setSampleRate:(UInt32) value {
+  result.hasSampleRate = YES;
+  result.sampleRate = value;
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clearSampleRate {
+  result.hasSampleRate = NO;
+  result.sampleRate = 0;
+  return self;
+}
+- (NSMutableArray *)privateData {
+  return result.privateDataArray;
+}
+- (NSData*)privateDataAtIndex:(NSUInteger)index {
+  return [result privateDataAtIndex:index];
+}
+- (PlaybackBeginStreamBuilder *)addPrivateData:(NSData*)value {
+  if (result.privateDataArray == nil) {
+    result.privateDataArray = [[NSMutableArray alloc]init];
+  }
+  [result.privateDataArray addObject:value];
+  return self;
+}
+- (PlaybackBeginStreamBuilder *)setPrivateDataArray:(NSArray *)array {
+  result.privateDataArray = [[NSMutableArray alloc] initWithArray:array];
+  return self;
+}
+- (PlaybackBeginStreamBuilder *)clearPrivateData {
+  result.privateDataArray = nil;
+  return self;
+}
+- (BOOL) hasStartTime {
+  return result.hasStartTime;
+}
+- (Float64) startTime {
+  return result.startTime;
+}
+- (PlaybackBeginStreamBuilder*) setStartTime:(Float64) value {
+  result.hasStartTime = YES;
+  result.startTime = value;
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clearStartTime {
+  result.hasStartTime = NO;
+  result.startTime = 0;
+  return self;
+}
+- (BOOL) hasUdpSsrc {
+  return result.hasUdpSsrc;
+}
+- (UInt32) udpSsrc {
+  return result.udpSsrc;
+}
+- (PlaybackBeginStreamBuilder*) setUdpSsrc:(UInt32) value {
+  result.hasUdpSsrc = YES;
+  result.udpSsrc = value;
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clearUdpSsrc {
+  result.hasUdpSsrc = NO;
+  result.udpSsrc = 0;
+  return self;
+}
+- (BOOL) hasRtpStartTime {
+  return result.hasRtpStartTime;
+}
+- (UInt32) rtpStartTime {
+  return result.rtpStartTime;
+}
+- (PlaybackBeginStreamBuilder*) setRtpStartTime:(UInt32) value {
+  result.hasRtpStartTime = YES;
+  result.rtpStartTime = value;
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clearRtpStartTime {
+  result.hasRtpStartTime = NO;
+  result.rtpStartTime = 0;
+  return self;
+}
+- (BOOL) hasProfile {
+  return result.hasProfile;
+}
+- (CT_AVProfile) profile {
+  return result.profile;
+}
+- (PlaybackBeginStreamBuilder*) setProfile:(CT_AVProfile) value {
+  result.hasProfile = YES;
+  result.profile = value;
+  return self;
+}
+- (PlaybackBeginStreamBuilder*) clearProfile {
+  result.hasProfile = NO;
+  result.profile = CT_AVProfileAudioAac;
+  return self;
+}
+@end
+
+@interface PlaybackBeginBuilder()
+@property (strong) PlaybackBegin* result;
+@end
+
+@implementation PlaybackBeginBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PlaybackBegin alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PlaybackBeginBuilder*) clear {
+  self.result = [[PlaybackBegin alloc] init];
+  return self;
+}
+- (PlaybackBeginBuilder*) clone {
+  return [PlaybackBegin builderWithPrototype:result];
+}
+- (PlaybackBegin*) defaultInstance {
+  return [PlaybackBegin defaultInstance];
+}
+- (PlaybackBegin*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PlaybackBegin*) buildPartial {
+  PlaybackBegin* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PlaybackBeginBuilder*) mergeFrom:(PlaybackBegin*) other {
+  if (other == [PlaybackBegin defaultInstance]) {
+    return self;
+  }
+  if (other.hasSessionId) {
+    [self setSessionId:other.sessionId];
+  }
+  if (other.channelsArray.count > 0) {
+    if (result.channelsArray == nil) {
+      result.channelsArray = [[NSMutableArray alloc] initWithArray:other.channelsArray];
+    } else {
+      [result.channelsArray addObjectsFromArray:other.channelsArray];
+    }
+  }
+  if (other.hasSrtpMasterKey) {
+    [self setSrtpMasterKey:other.srtpMasterKey];
+  }
+  if (other.hasSrtpMasterSalt) {
+    [self setSrtpMasterSalt:other.srtpMasterSalt];
+  }
+  if (other.hasFecKVal) {
+    [self setFecKVal:other.fecKVal];
+  }
+  if (other.hasFecNVal) {
+    [self setFecNVal:other.fecNVal];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PlaybackBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PlaybackBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setSessionId:[input readUInt32]];
+        break;
+      }
+      case 18: {
+        PlaybackBeginStreamBuilder* subBuilder = [PlaybackBeginStream builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addChannels:[subBuilder buildPartial]];
+        break;
+      }
+      case 26: {
+        [self setSrtpMasterKey:[input readData]];
+        break;
+      }
+      case 34: {
+        [self setSrtpMasterSalt:[input readData]];
+        break;
+      }
+      case 40: {
+        [self setFecKVal:[input readUInt32]];
+        break;
+      }
+      case 48: {
+        [self setFecNVal:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasSessionId {
+  return result.hasSessionId;
+}
+- (UInt32) sessionId {
+  return result.sessionId;
+}
+- (PlaybackBeginBuilder*) setSessionId:(UInt32) value {
+  result.hasSessionId = YES;
+  result.sessionId = value;
+  return self;
+}
+- (PlaybackBeginBuilder*) clearSessionId {
+  result.hasSessionId = NO;
+  result.sessionId = 0;
+  return self;
+}
+- (NSMutableArray *)channels {
+  return result.channelsArray;
+}
+- (PlaybackBeginStream*)channelsAtIndex:(NSUInteger)index {
+  return [result channelsAtIndex:index];
+}
+- (PlaybackBeginBuilder *)addChannels:(PlaybackBeginStream*)value {
+  if (result.channelsArray == nil) {
+    result.channelsArray = [[NSMutableArray alloc]init];
+  }
+  [result.channelsArray addObject:value];
+  return self;
+}
+- (PlaybackBeginBuilder *)setChannelsArray:(NSArray *)array {
+  result.channelsArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PlaybackBeginBuilder *)clearChannels {
+  result.channelsArray = nil;
+  return self;
+}
+- (BOOL) hasSrtpMasterKey {
+  return result.hasSrtpMasterKey;
+}
+- (NSData*) srtpMasterKey {
+  return result.srtpMasterKey;
+}
+- (PlaybackBeginBuilder*) setSrtpMasterKey:(NSData*) value {
+  result.hasSrtpMasterKey = YES;
+  result.srtpMasterKey = value;
+  return self;
+}
+- (PlaybackBeginBuilder*) clearSrtpMasterKey {
+  result.hasSrtpMasterKey = NO;
+  result.srtpMasterKey = [NSData data];
+  return self;
+}
+- (BOOL) hasSrtpMasterSalt {
+  return result.hasSrtpMasterSalt;
+}
+- (NSData*) srtpMasterSalt {
+  return result.srtpMasterSalt;
+}
+- (PlaybackBeginBuilder*) setSrtpMasterSalt:(NSData*) value {
+  result.hasSrtpMasterSalt = YES;
+  result.srtpMasterSalt = value;
+  return self;
+}
+- (PlaybackBeginBuilder*) clearSrtpMasterSalt {
+  result.hasSrtpMasterSalt = NO;
+  result.srtpMasterSalt = [NSData data];
+  return self;
+}
+- (BOOL) hasFecKVal {
+  return result.hasFecKVal;
+}
+- (UInt32) fecKVal {
+  return result.fecKVal;
+}
+- (PlaybackBeginBuilder*) setFecKVal:(UInt32) value {
+  result.hasFecKVal = YES;
+  result.fecKVal = value;
+  return self;
+}
+- (PlaybackBeginBuilder*) clearFecKVal {
+  result.hasFecKVal = NO;
+  result.fecKVal = 0;
+  return self;
+}
+- (BOOL) hasFecNVal {
+  return result.hasFecNVal;
+}
+- (UInt32) fecNVal {
+  return result.fecNVal;
+}
+- (PlaybackBeginBuilder*) setFecNVal:(UInt32) value {
+  result.hasFecNVal = YES;
+  result.fecNVal = value;
+  return self;
+}
+- (PlaybackBeginBuilder*) clearFecNVal {
+  result.hasFecNVal = NO;
+  result.fecNVal = 0;
+  return self;
+}
+@end
+
+@interface PlaybackEnd ()
+@property UInt32 sessionId;
+@property PlaybackEndReason reason;
+@end
+
+@implementation PlaybackEnd
+
+- (BOOL) hasSessionId {
+  return !!hasSessionId_;
+}
+- (void) setHasSessionId:(BOOL) value_ {
+  hasSessionId_ = !!value_;
+}
+@synthesize sessionId;
+- (BOOL) hasReason {
+  return !!hasReason_;
+}
+- (void) setHasReason:(BOOL) value_ {
+  hasReason_ = !!value_;
+}
+@synthesize reason;
+- (id) init {
+  if ((self = [super init])) {
+    self.sessionId = 0;
+    self.reason = PlaybackEndReasonErrorTimeNotAvailable;
+  }
+  return self;
+}
+static PlaybackEnd* defaultPlaybackEndInstance = nil;
++ (void) initialize {
+  if (self == [PlaybackEnd class]) {
+    defaultPlaybackEndInstance = [[PlaybackEnd alloc] init];
+  }
+}
++ (PlaybackEnd*) defaultInstance {
+  return defaultPlaybackEndInstance;
+}
+- (PlaybackEnd*) defaultInstance {
+  return defaultPlaybackEndInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasSessionId) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasSessionId) {
+    [output writeUInt32:1 value:self.sessionId];
+  }
+  if (self.hasReason) {
+    [output writeEnum:2 value:self.reason];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasSessionId) {
+    size_ += computeUInt32Size(1, self.sessionId);
+  }
+  if (self.hasReason) {
+    size_ += computeEnumSize(2, self.reason);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PlaybackEnd*) parseFromData:(NSData*) data {
+  return (PlaybackEnd*)[[[PlaybackEnd builder] mergeFromData:data] build];
+}
++ (PlaybackEnd*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackEnd*)[[[PlaybackEnd builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackEnd*) parseFromInputStream:(NSInputStream*) input {
+  return (PlaybackEnd*)[[[PlaybackEnd builder] mergeFromInputStream:input] build];
+}
++ (PlaybackEnd*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackEnd*)[[[PlaybackEnd builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackEnd*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PlaybackEnd*)[[[PlaybackEnd builder] mergeFromCodedInputStream:input] build];
+}
++ (PlaybackEnd*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackEnd*)[[[PlaybackEnd builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackEndBuilder*) builder {
+  return [[PlaybackEndBuilder alloc] init];
+}
++ (PlaybackEndBuilder*) builderWithPrototype:(PlaybackEnd*) prototype {
+  return [[PlaybackEnd builder] mergeFrom:prototype];
+}
+- (PlaybackEndBuilder*) builder {
+  return [PlaybackEnd builder];
+}
+- (PlaybackEndBuilder*) toBuilder {
+  return [PlaybackEnd builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasSessionId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionId", [NSNumber numberWithInteger:self.sessionId]];
+  }
+  if (self.hasReason) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"reason", self.reason];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PlaybackEnd class]]) {
+    return NO;
+  }
+  PlaybackEnd *otherMessage = other;
+  return
+      self.hasSessionId == otherMessage.hasSessionId &&
+      (!self.hasSessionId || self.sessionId == otherMessage.sessionId) &&
+      self.hasReason == otherMessage.hasReason &&
+      (!self.hasReason || self.reason == otherMessage.reason) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasSessionId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sessionId] hash];
+  }
+  if (self.hasReason) {
+    hashCode = hashCode * 31 + self.reason;
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL PlaybackEndReasonIsValidValue(PlaybackEndReason value) {
+  switch (value) {
+    case PlaybackEndReasonErrorTimeNotAvailable:
+    case PlaybackEndReasonErrorProfileNotAvailable:
+    case PlaybackEndReasonErrorTranscodeNotAvailable:
+    case PlaybackEndReasonPlayEndSessionComplete:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface PlaybackEndBuilder()
+@property (strong) PlaybackEnd* result;
+@end
+
+@implementation PlaybackEndBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PlaybackEnd alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PlaybackEndBuilder*) clear {
+  self.result = [[PlaybackEnd alloc] init];
+  return self;
+}
+- (PlaybackEndBuilder*) clone {
+  return [PlaybackEnd builderWithPrototype:result];
+}
+- (PlaybackEnd*) defaultInstance {
+  return [PlaybackEnd defaultInstance];
+}
+- (PlaybackEnd*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PlaybackEnd*) buildPartial {
+  PlaybackEnd* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PlaybackEndBuilder*) mergeFrom:(PlaybackEnd*) other {
+  if (other == [PlaybackEnd defaultInstance]) {
+    return self;
+  }
+  if (other.hasSessionId) {
+    [self setSessionId:other.sessionId];
+  }
+  if (other.hasReason) {
+    [self setReason:other.reason];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PlaybackEndBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PlaybackEndBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setSessionId:[input readUInt32]];
+        break;
+      }
+      case 16: {
+        PlaybackEndReason value = (PlaybackEndReason)[input readEnum];
+        if (PlaybackEndReasonIsValidValue(value)) {
+          [self setReason:value];
+        } else {
+          [unknownFields mergeVarintField:2 value:value];
+        }
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasSessionId {
+  return result.hasSessionId;
+}
+- (UInt32) sessionId {
+  return result.sessionId;
+}
+- (PlaybackEndBuilder*) setSessionId:(UInt32) value {
+  result.hasSessionId = YES;
+  result.sessionId = value;
+  return self;
+}
+- (PlaybackEndBuilder*) clearSessionId {
+  result.hasSessionId = NO;
+  result.sessionId = 0;
+  return self;
+}
+- (BOOL) hasReason {
+  return result.hasReason;
+}
+- (PlaybackEndReason) reason {
+  return result.reason;
+}
+- (PlaybackEndBuilder*) setReason:(PlaybackEndReason) value {
+  result.hasReason = YES;
+  result.reason = value;
+  return self;
+}
+- (PlaybackEndBuilder*) clearReason {
+  result.hasReason = NO;
+  result.reason = PlaybackEndReasonErrorTimeNotAvailable;
+  return self;
+}
+@end
+
+@interface PlaybackPacket ()
+@property UInt32 sessionId;
+@property UInt32 channelId;
+@property SInt32 timestampDelta;
+@property (strong) NSData* payload;
+@property UInt32 latencyRtpSequence;
+@property UInt32 latencyRtpSsrc;
+@end
+
+@implementation PlaybackPacket
+
+- (BOOL) hasSessionId {
+  return !!hasSessionId_;
+}
+- (void) setHasSessionId:(BOOL) value_ {
+  hasSessionId_ = !!value_;
+}
+@synthesize sessionId;
+- (BOOL) hasChannelId {
+  return !!hasChannelId_;
+}
+- (void) setHasChannelId:(BOOL) value_ {
+  hasChannelId_ = !!value_;
+}
+@synthesize channelId;
+- (BOOL) hasTimestampDelta {
+  return !!hasTimestampDelta_;
+}
+- (void) setHasTimestampDelta:(BOOL) value_ {
+  hasTimestampDelta_ = !!value_;
+}
+@synthesize timestampDelta;
+- (BOOL) hasPayload {
+  return !!hasPayload_;
+}
+- (void) setHasPayload:(BOOL) value_ {
+  hasPayload_ = !!value_;
+}
+@synthesize payload;
+- (BOOL) hasLatencyRtpSequence {
+  return !!hasLatencyRtpSequence_;
+}
+- (void) setHasLatencyRtpSequence:(BOOL) value_ {
+  hasLatencyRtpSequence_ = !!value_;
+}
+@synthesize latencyRtpSequence;
+- (BOOL) hasLatencyRtpSsrc {
+  return !!hasLatencyRtpSsrc_;
+}
+- (void) setHasLatencyRtpSsrc:(BOOL) value_ {
+  hasLatencyRtpSsrc_ = !!value_;
+}
+@synthesize latencyRtpSsrc;
+- (id) init {
+  if ((self = [super init])) {
+    self.sessionId = 0;
+    self.channelId = 0;
+    self.timestampDelta = 0;
+    self.payload = [NSData data];
+    self.latencyRtpSequence = 0;
+    self.latencyRtpSsrc = 0;
+  }
+  return self;
+}
+static PlaybackPacket* defaultPlaybackPacketInstance = nil;
++ (void) initialize {
+  if (self == [PlaybackPacket class]) {
+    defaultPlaybackPacketInstance = [[PlaybackPacket alloc] init];
+  }
+}
++ (PlaybackPacket*) defaultInstance {
+  return defaultPlaybackPacketInstance;
+}
+- (PlaybackPacket*) defaultInstance {
+  return defaultPlaybackPacketInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasSessionId) {
+    return NO;
+  }
+  if (!self.hasChannelId) {
+    return NO;
+  }
+  if (!self.hasTimestampDelta) {
+    return NO;
+  }
+  if (!self.hasPayload) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasSessionId) {
+    [output writeUInt32:1 value:self.sessionId];
+  }
+  if (self.hasChannelId) {
+    [output writeUInt32:2 value:self.channelId];
+  }
+  if (self.hasTimestampDelta) {
+    [output writeSInt32:3 value:self.timestampDelta];
+  }
+  if (self.hasPayload) {
+    [output writeData:4 value:self.payload];
+  }
+  if (self.hasLatencyRtpSequence) {
+    [output writeUInt32:5 value:self.latencyRtpSequence];
+  }
+  if (self.hasLatencyRtpSsrc) {
+    [output writeUInt32:6 value:self.latencyRtpSsrc];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasSessionId) {
+    size_ += computeUInt32Size(1, self.sessionId);
+  }
+  if (self.hasChannelId) {
+    size_ += computeUInt32Size(2, self.channelId);
+  }
+  if (self.hasTimestampDelta) {
+    size_ += computeSInt32Size(3, self.timestampDelta);
+  }
+  if (self.hasPayload) {
+    size_ += computeDataSize(4, self.payload);
+  }
+  if (self.hasLatencyRtpSequence) {
+    size_ += computeUInt32Size(5, self.latencyRtpSequence);
+  }
+  if (self.hasLatencyRtpSsrc) {
+    size_ += computeUInt32Size(6, self.latencyRtpSsrc);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PlaybackPacket*) parseFromData:(NSData*) data {
+  return (PlaybackPacket*)[[[PlaybackPacket builder] mergeFromData:data] build];
+}
++ (PlaybackPacket*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackPacket*)[[[PlaybackPacket builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackPacket*) parseFromInputStream:(NSInputStream*) input {
+  return (PlaybackPacket*)[[[PlaybackPacket builder] mergeFromInputStream:input] build];
+}
++ (PlaybackPacket*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackPacket*)[[[PlaybackPacket builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackPacket*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PlaybackPacket*)[[[PlaybackPacket builder] mergeFromCodedInputStream:input] build];
+}
++ (PlaybackPacket*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PlaybackPacket*)[[[PlaybackPacket builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PlaybackPacketBuilder*) builder {
+  return [[PlaybackPacketBuilder alloc] init];
+}
++ (PlaybackPacketBuilder*) builderWithPrototype:(PlaybackPacket*) prototype {
+  return [[PlaybackPacket builder] mergeFrom:prototype];
+}
+- (PlaybackPacketBuilder*) builder {
+  return [PlaybackPacket builder];
+}
+- (PlaybackPacketBuilder*) toBuilder {
+  return [PlaybackPacket builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasSessionId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionId", [NSNumber numberWithInteger:self.sessionId]];
+  }
+  if (self.hasChannelId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"channelId", [NSNumber numberWithInteger:self.channelId]];
+  }
+  if (self.hasTimestampDelta) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"timestampDelta", [NSNumber numberWithInteger:self.timestampDelta]];
+  }
+  if (self.hasPayload) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"payload", self.payload];
+  }
+  if (self.hasLatencyRtpSequence) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"latencyRtpSequence", [NSNumber numberWithInteger:self.latencyRtpSequence]];
+  }
+  if (self.hasLatencyRtpSsrc) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"latencyRtpSsrc", [NSNumber numberWithInteger:self.latencyRtpSsrc]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PlaybackPacket class]]) {
+    return NO;
+  }
+  PlaybackPacket *otherMessage = other;
+  return
+      self.hasSessionId == otherMessage.hasSessionId &&
+      (!self.hasSessionId || self.sessionId == otherMessage.sessionId) &&
+      self.hasChannelId == otherMessage.hasChannelId &&
+      (!self.hasChannelId || self.channelId == otherMessage.channelId) &&
+      self.hasTimestampDelta == otherMessage.hasTimestampDelta &&
+      (!self.hasTimestampDelta || self.timestampDelta == otherMessage.timestampDelta) &&
+      self.hasPayload == otherMessage.hasPayload &&
+      (!self.hasPayload || [self.payload isEqual:otherMessage.payload]) &&
+      self.hasLatencyRtpSequence == otherMessage.hasLatencyRtpSequence &&
+      (!self.hasLatencyRtpSequence || self.latencyRtpSequence == otherMessage.latencyRtpSequence) &&
+      self.hasLatencyRtpSsrc == otherMessage.hasLatencyRtpSsrc &&
+      (!self.hasLatencyRtpSsrc || self.latencyRtpSsrc == otherMessage.latencyRtpSsrc) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasSessionId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.sessionId] hash];
+  }
+  if (self.hasChannelId) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.channelId] hash];
+  }
+  if (self.hasTimestampDelta) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.timestampDelta] hash];
+  }
+  if (self.hasPayload) {
+    hashCode = hashCode * 31 + [self.payload hash];
+  }
+  if (self.hasLatencyRtpSequence) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.latencyRtpSequence] hash];
+  }
+  if (self.hasLatencyRtpSsrc) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.latencyRtpSsrc] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PlaybackPacketBuilder()
+@property (strong) PlaybackPacket* result;
+@end
+
+@implementation PlaybackPacketBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PlaybackPacket alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PlaybackPacketBuilder*) clear {
+  self.result = [[PlaybackPacket alloc] init];
+  return self;
+}
+- (PlaybackPacketBuilder*) clone {
+  return [PlaybackPacket builderWithPrototype:result];
+}
+- (PlaybackPacket*) defaultInstance {
+  return [PlaybackPacket defaultInstance];
+}
+- (PlaybackPacket*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PlaybackPacket*) buildPartial {
+  PlaybackPacket* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PlaybackPacketBuilder*) mergeFrom:(PlaybackPacket*) other {
+  if (other == [PlaybackPacket defaultInstance]) {
+    return self;
+  }
+  if (other.hasSessionId) {
+    [self setSessionId:other.sessionId];
+  }
+  if (other.hasChannelId) {
+    [self setChannelId:other.channelId];
+  }
+  if (other.hasTimestampDelta) {
+    [self setTimestampDelta:other.timestampDelta];
+  }
+  if (other.hasPayload) {
+    [self setPayload:other.payload];
+  }
+  if (other.hasLatencyRtpSequence) {
+    [self setLatencyRtpSequence:other.latencyRtpSequence];
+  }
+  if (other.hasLatencyRtpSsrc) {
+    [self setLatencyRtpSsrc:other.latencyRtpSsrc];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PlaybackPacketBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PlaybackPacketBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setSessionId:[input readUInt32]];
+        break;
+      }
+      case 16: {
+        [self setChannelId:[input readUInt32]];
+        break;
+      }
+      case 24: {
+        [self setTimestampDelta:[input readSInt32]];
+        break;
+      }
+      case 34: {
+        [self setPayload:[input readData]];
+        break;
+      }
+      case 40: {
+        [self setLatencyRtpSequence:[input readUInt32]];
+        break;
+      }
+      case 48: {
+        [self setLatencyRtpSsrc:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasSessionId {
+  return result.hasSessionId;
+}
+- (UInt32) sessionId {
+  return result.sessionId;
+}
+- (PlaybackPacketBuilder*) setSessionId:(UInt32) value {
+  result.hasSessionId = YES;
+  result.sessionId = value;
+  return self;
+}
+- (PlaybackPacketBuilder*) clearSessionId {
+  result.hasSessionId = NO;
+  result.sessionId = 0;
+  return self;
+}
+- (BOOL) hasChannelId {
+  return result.hasChannelId;
+}
+- (UInt32) channelId {
+  return result.channelId;
+}
+- (PlaybackPacketBuilder*) setChannelId:(UInt32) value {
+  result.hasChannelId = YES;
+  result.channelId = value;
+  return self;
+}
+- (PlaybackPacketBuilder*) clearChannelId {
+  result.hasChannelId = NO;
+  result.channelId = 0;
+  return self;
+}
+- (BOOL) hasTimestampDelta {
+  return result.hasTimestampDelta;
+}
+- (SInt32) timestampDelta {
+  return result.timestampDelta;
+}
+- (PlaybackPacketBuilder*) setTimestampDelta:(SInt32) value {
+  result.hasTimestampDelta = YES;
+  result.timestampDelta = value;
+  return self;
+}
+- (PlaybackPacketBuilder*) clearTimestampDelta {
+  result.hasTimestampDelta = NO;
+  result.timestampDelta = 0;
+  return self;
+}
+- (BOOL) hasPayload {
+  return result.hasPayload;
+}
+- (NSData*) payload {
+  return result.payload;
+}
+- (PlaybackPacketBuilder*) setPayload:(NSData*) value {
+  result.hasPayload = YES;
+  result.payload = value;
+  return self;
+}
+- (PlaybackPacketBuilder*) clearPayload {
+  result.hasPayload = NO;
+  result.payload = [NSData data];
+  return self;
+}
+- (BOOL) hasLatencyRtpSequence {
+  return result.hasLatencyRtpSequence;
+}
+- (UInt32) latencyRtpSequence {
+  return result.latencyRtpSequence;
+}
+- (PlaybackPacketBuilder*) setLatencyRtpSequence:(UInt32) value {
+  result.hasLatencyRtpSequence = YES;
+  result.latencyRtpSequence = value;
+  return self;
+}
+- (PlaybackPacketBuilder*) clearLatencyRtpSequence {
+  result.hasLatencyRtpSequence = NO;
+  result.latencyRtpSequence = 0;
+  return self;
+}
+- (BOOL) hasLatencyRtpSsrc {
+  return result.hasLatencyRtpSsrc;
+}
+- (UInt32) latencyRtpSsrc {
+  return result.latencyRtpSsrc;
+}
+- (PlaybackPacketBuilder*) setLatencyRtpSsrc:(UInt32) value {
+  result.hasLatencyRtpSsrc = YES;
+  result.latencyRtpSsrc = value;
+  return self;
+}
+- (PlaybackPacketBuilder*) clearLatencyRtpSsrc {
+  result.hasLatencyRtpSsrc = NO;
+  result.latencyRtpSsrc = 0;
+  return self;
+}
+@end
+
+@interface ClockSync ()
+@property UInt32 serverSystemTimeSec;
+@property UInt32 serverSystemTimeMsec;
+@end
+
+@implementation ClockSync
+
+- (BOOL) hasServerSystemTimeSec {
+  return !!hasServerSystemTimeSec_;
+}
+- (void) setHasServerSystemTimeSec:(BOOL) value_ {
+  hasServerSystemTimeSec_ = !!value_;
+}
+@synthesize serverSystemTimeSec;
+- (BOOL) hasServerSystemTimeMsec {
+  return !!hasServerSystemTimeMsec_;
+}
+- (void) setHasServerSystemTimeMsec:(BOOL) value_ {
+  hasServerSystemTimeMsec_ = !!value_;
+}
+@synthesize serverSystemTimeMsec;
+- (id) init {
+  if ((self = [super init])) {
+    self.serverSystemTimeSec = 0;
+    self.serverSystemTimeMsec = 0;
+  }
+  return self;
+}
+static ClockSync* defaultClockSyncInstance = nil;
++ (void) initialize {
+  if (self == [ClockSync class]) {
+    defaultClockSyncInstance = [[ClockSync alloc] init];
+  }
+}
++ (ClockSync*) defaultInstance {
+  return defaultClockSyncInstance;
+}
+- (ClockSync*) defaultInstance {
+  return defaultClockSyncInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasServerSystemTimeSec) {
+    return NO;
+  }
+  if (!self.hasServerSystemTimeMsec) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasServerSystemTimeSec) {
+    [output writeUInt32:1 value:self.serverSystemTimeSec];
+  }
+  if (self.hasServerSystemTimeMsec) {
+    [output writeUInt32:2 value:self.serverSystemTimeMsec];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasServerSystemTimeSec) {
+    size_ += computeUInt32Size(1, self.serverSystemTimeSec);
+  }
+  if (self.hasServerSystemTimeMsec) {
+    size_ += computeUInt32Size(2, self.serverSystemTimeMsec);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ClockSync*) parseFromData:(NSData*) data {
+  return (ClockSync*)[[[ClockSync builder] mergeFromData:data] build];
+}
++ (ClockSync*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ClockSync*)[[[ClockSync builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ClockSync*) parseFromInputStream:(NSInputStream*) input {
+  return (ClockSync*)[[[ClockSync builder] mergeFromInputStream:input] build];
+}
++ (ClockSync*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ClockSync*)[[[ClockSync builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ClockSync*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ClockSync*)[[[ClockSync builder] mergeFromCodedInputStream:input] build];
+}
++ (ClockSync*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ClockSync*)[[[ClockSync builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ClockSyncBuilder*) builder {
+  return [[ClockSyncBuilder alloc] init];
+}
++ (ClockSyncBuilder*) builderWithPrototype:(ClockSync*) prototype {
+  return [[ClockSync builder] mergeFrom:prototype];
+}
+- (ClockSyncBuilder*) builder {
+  return [ClockSync builder];
+}
+- (ClockSyncBuilder*) toBuilder {
+  return [ClockSync builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasServerSystemTimeSec) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"serverSystemTimeSec", [NSNumber numberWithInteger:self.serverSystemTimeSec]];
+  }
+  if (self.hasServerSystemTimeMsec) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"serverSystemTimeMsec", [NSNumber numberWithInteger:self.serverSystemTimeMsec]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ClockSync class]]) {
+    return NO;
+  }
+  ClockSync *otherMessage = other;
+  return
+      self.hasServerSystemTimeSec == otherMessage.hasServerSystemTimeSec &&
+      (!self.hasServerSystemTimeSec || self.serverSystemTimeSec == otherMessage.serverSystemTimeSec) &&
+      self.hasServerSystemTimeMsec == otherMessage.hasServerSystemTimeMsec &&
+      (!self.hasServerSystemTimeMsec || self.serverSystemTimeMsec == otherMessage.serverSystemTimeMsec) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasServerSystemTimeSec) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.serverSystemTimeSec] hash];
+  }
+  if (self.hasServerSystemTimeMsec) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.serverSystemTimeMsec] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ClockSyncBuilder()
+@property (strong) ClockSync* result;
+@end
+
+@implementation ClockSyncBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ClockSync alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ClockSyncBuilder*) clear {
+  self.result = [[ClockSync alloc] init];
+  return self;
+}
+- (ClockSyncBuilder*) clone {
+  return [ClockSync builderWithPrototype:result];
+}
+- (ClockSync*) defaultInstance {
+  return [ClockSync defaultInstance];
+}
+- (ClockSync*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ClockSync*) buildPartial {
+  ClockSync* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ClockSyncBuilder*) mergeFrom:(ClockSync*) other {
+  if (other == [ClockSync defaultInstance]) {
+    return self;
+  }
+  if (other.hasServerSystemTimeSec) {
+    [self setServerSystemTimeSec:other.serverSystemTimeSec];
+  }
+  if (other.hasServerSystemTimeMsec) {
+    [self setServerSystemTimeMsec:other.serverSystemTimeMsec];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ClockSyncBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ClockSyncBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setServerSystemTimeSec:[input readUInt32]];
+        break;
+      }
+      case 16: {
+        [self setServerSystemTimeMsec:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasServerSystemTimeSec {
+  return result.hasServerSystemTimeSec;
+}
+- (UInt32) serverSystemTimeSec {
+  return result.serverSystemTimeSec;
+}
+- (ClockSyncBuilder*) setServerSystemTimeSec:(UInt32) value {
+  result.hasServerSystemTimeSec = YES;
+  result.serverSystemTimeSec = value;
+  return self;
+}
+- (ClockSyncBuilder*) clearServerSystemTimeSec {
+  result.hasServerSystemTimeSec = NO;
+  result.serverSystemTimeSec = 0;
+  return self;
+}
+- (BOOL) hasServerSystemTimeMsec {
+  return result.hasServerSystemTimeMsec;
+}
+- (UInt32) serverSystemTimeMsec {
+  return result.serverSystemTimeMsec;
+}
+- (ClockSyncBuilder*) setServerSystemTimeMsec:(UInt32) value {
+  result.hasServerSystemTimeMsec = YES;
+  result.serverSystemTimeMsec = value;
+  return self;
+}
+- (ClockSyncBuilder*) clearServerSystemTimeMsec {
+  result.hasServerSystemTimeMsec = NO;
+  result.serverSystemTimeMsec = 0;
+  return self;
+}
+@end
+
+@interface ClockSyncEcho ()
+@property UInt32 serverSystemTimeEchoSec;
+@property UInt32 serverSystemTimeEchoMsec;
+@property UInt32 clientSystemTimeSec;
+@property UInt32 clientSystemTimeMsec;
+@end
+
+@implementation ClockSyncEcho
+
+- (BOOL) hasServerSystemTimeEchoSec {
+  return !!hasServerSystemTimeEchoSec_;
+}
+- (void) setHasServerSystemTimeEchoSec:(BOOL) value_ {
+  hasServerSystemTimeEchoSec_ = !!value_;
+}
+@synthesize serverSystemTimeEchoSec;
+- (BOOL) hasServerSystemTimeEchoMsec {
+  return !!hasServerSystemTimeEchoMsec_;
+}
+- (void) setHasServerSystemTimeEchoMsec:(BOOL) value_ {
+  hasServerSystemTimeEchoMsec_ = !!value_;
+}
+@synthesize serverSystemTimeEchoMsec;
+- (BOOL) hasClientSystemTimeSec {
+  return !!hasClientSystemTimeSec_;
+}
+- (void) setHasClientSystemTimeSec:(BOOL) value_ {
+  hasClientSystemTimeSec_ = !!value_;
+}
+@synthesize clientSystemTimeSec;
+- (BOOL) hasClientSystemTimeMsec {
+  return !!hasClientSystemTimeMsec_;
+}
+- (void) setHasClientSystemTimeMsec:(BOOL) value_ {
+  hasClientSystemTimeMsec_ = !!value_;
+}
+@synthesize clientSystemTimeMsec;
+- (id) init {
+  if ((self = [super init])) {
+    self.serverSystemTimeEchoSec = 0;
+    self.serverSystemTimeEchoMsec = 0;
+    self.clientSystemTimeSec = 0;
+    self.clientSystemTimeMsec = 0;
+  }
+  return self;
+}
+static ClockSyncEcho* defaultClockSyncEchoInstance = nil;
++ (void) initialize {
+  if (self == [ClockSyncEcho class]) {
+    defaultClockSyncEchoInstance = [[ClockSyncEcho alloc] init];
+  }
+}
++ (ClockSyncEcho*) defaultInstance {
+  return defaultClockSyncEchoInstance;
+}
+- (ClockSyncEcho*) defaultInstance {
+  return defaultClockSyncEchoInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasServerSystemTimeEchoSec) {
+    return NO;
+  }
+  if (!self.hasServerSystemTimeEchoMsec) {
+    return NO;
+  }
+  if (!self.hasClientSystemTimeSec) {
+    return NO;
+  }
+  if (!self.hasClientSystemTimeMsec) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasServerSystemTimeEchoSec) {
+    [output writeUInt32:1 value:self.serverSystemTimeEchoSec];
+  }
+  if (self.hasServerSystemTimeEchoMsec) {
+    [output writeUInt32:2 value:self.serverSystemTimeEchoMsec];
+  }
+  if (self.hasClientSystemTimeSec) {
+    [output writeUInt32:3 value:self.clientSystemTimeSec];
+  }
+  if (self.hasClientSystemTimeMsec) {
+    [output writeUInt32:4 value:self.clientSystemTimeMsec];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasServerSystemTimeEchoSec) {
+    size_ += computeUInt32Size(1, self.serverSystemTimeEchoSec);
+  }
+  if (self.hasServerSystemTimeEchoMsec) {
+    size_ += computeUInt32Size(2, self.serverSystemTimeEchoMsec);
+  }
+  if (self.hasClientSystemTimeSec) {
+    size_ += computeUInt32Size(3, self.clientSystemTimeSec);
+  }
+  if (self.hasClientSystemTimeMsec) {
+    size_ += computeUInt32Size(4, self.clientSystemTimeMsec);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ClockSyncEcho*) parseFromData:(NSData*) data {
+  return (ClockSyncEcho*)[[[ClockSyncEcho builder] mergeFromData:data] build];
+}
++ (ClockSyncEcho*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ClockSyncEcho*)[[[ClockSyncEcho builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ClockSyncEcho*) parseFromInputStream:(NSInputStream*) input {
+  return (ClockSyncEcho*)[[[ClockSyncEcho builder] mergeFromInputStream:input] build];
+}
++ (ClockSyncEcho*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ClockSyncEcho*)[[[ClockSyncEcho builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ClockSyncEcho*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ClockSyncEcho*)[[[ClockSyncEcho builder] mergeFromCodedInputStream:input] build];
+}
++ (ClockSyncEcho*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ClockSyncEcho*)[[[ClockSyncEcho builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ClockSyncEchoBuilder*) builder {
+  return [[ClockSyncEchoBuilder alloc] init];
+}
++ (ClockSyncEchoBuilder*) builderWithPrototype:(ClockSyncEcho*) prototype {
+  return [[ClockSyncEcho builder] mergeFrom:prototype];
+}
+- (ClockSyncEchoBuilder*) builder {
+  return [ClockSyncEcho builder];
+}
+- (ClockSyncEchoBuilder*) toBuilder {
+  return [ClockSyncEcho builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasServerSystemTimeEchoSec) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"serverSystemTimeEchoSec", [NSNumber numberWithInteger:self.serverSystemTimeEchoSec]];
+  }
+  if (self.hasServerSystemTimeEchoMsec) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"serverSystemTimeEchoMsec", [NSNumber numberWithInteger:self.serverSystemTimeEchoMsec]];
+  }
+  if (self.hasClientSystemTimeSec) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"clientSystemTimeSec", [NSNumber numberWithInteger:self.clientSystemTimeSec]];
+  }
+  if (self.hasClientSystemTimeMsec) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"clientSystemTimeMsec", [NSNumber numberWithInteger:self.clientSystemTimeMsec]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ClockSyncEcho class]]) {
+    return NO;
+  }
+  ClockSyncEcho *otherMessage = other;
+  return
+      self.hasServerSystemTimeEchoSec == otherMessage.hasServerSystemTimeEchoSec &&
+      (!self.hasServerSystemTimeEchoSec || self.serverSystemTimeEchoSec == otherMessage.serverSystemTimeEchoSec) &&
+      self.hasServerSystemTimeEchoMsec == otherMessage.hasServerSystemTimeEchoMsec &&
+      (!self.hasServerSystemTimeEchoMsec || self.serverSystemTimeEchoMsec == otherMessage.serverSystemTimeEchoMsec) &&
+      self.hasClientSystemTimeSec == otherMessage.hasClientSystemTimeSec &&
+      (!self.hasClientSystemTimeSec || self.clientSystemTimeSec == otherMessage.clientSystemTimeSec) &&
+      self.hasClientSystemTimeMsec == otherMessage.hasClientSystemTimeMsec &&
+      (!self.hasClientSystemTimeMsec || self.clientSystemTimeMsec == otherMessage.clientSystemTimeMsec) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasServerSystemTimeEchoSec) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.serverSystemTimeEchoSec] hash];
+  }
+  if (self.hasServerSystemTimeEchoMsec) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.serverSystemTimeEchoMsec] hash];
+  }
+  if (self.hasClientSystemTimeSec) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.clientSystemTimeSec] hash];
+  }
+  if (self.hasClientSystemTimeMsec) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.clientSystemTimeMsec] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ClockSyncEchoBuilder()
+@property (strong) ClockSyncEcho* result;
+@end
+
+@implementation ClockSyncEchoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ClockSyncEcho alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ClockSyncEchoBuilder*) clear {
+  self.result = [[ClockSyncEcho alloc] init];
+  return self;
+}
+- (ClockSyncEchoBuilder*) clone {
+  return [ClockSyncEcho builderWithPrototype:result];
+}
+- (ClockSyncEcho*) defaultInstance {
+  return [ClockSyncEcho defaultInstance];
+}
+- (ClockSyncEcho*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ClockSyncEcho*) buildPartial {
+  ClockSyncEcho* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ClockSyncEchoBuilder*) mergeFrom:(ClockSyncEcho*) other {
+  if (other == [ClockSyncEcho defaultInstance]) {
+    return self;
+  }
+  if (other.hasServerSystemTimeEchoSec) {
+    [self setServerSystemTimeEchoSec:other.serverSystemTimeEchoSec];
+  }
+  if (other.hasServerSystemTimeEchoMsec) {
+    [self setServerSystemTimeEchoMsec:other.serverSystemTimeEchoMsec];
+  }
+  if (other.hasClientSystemTimeSec) {
+    [self setClientSystemTimeSec:other.clientSystemTimeSec];
+  }
+  if (other.hasClientSystemTimeMsec) {
+    [self setClientSystemTimeMsec:other.clientSystemTimeMsec];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ClockSyncEchoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ClockSyncEchoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setServerSystemTimeEchoSec:[input readUInt32]];
+        break;
+      }
+      case 16: {
+        [self setServerSystemTimeEchoMsec:[input readUInt32]];
+        break;
+      }
+      case 24: {
+        [self setClientSystemTimeSec:[input readUInt32]];
+        break;
+      }
+      case 32: {
+        [self setClientSystemTimeMsec:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasServerSystemTimeEchoSec {
+  return result.hasServerSystemTimeEchoSec;
+}
+- (UInt32) serverSystemTimeEchoSec {
+  return result.serverSystemTimeEchoSec;
+}
+- (ClockSyncEchoBuilder*) setServerSystemTimeEchoSec:(UInt32) value {
+  result.hasServerSystemTimeEchoSec = YES;
+  result.serverSystemTimeEchoSec = value;
+  return self;
+}
+- (ClockSyncEchoBuilder*) clearServerSystemTimeEchoSec {
+  result.hasServerSystemTimeEchoSec = NO;
+  result.serverSystemTimeEchoSec = 0;
+  return self;
+}
+- (BOOL) hasServerSystemTimeEchoMsec {
+  return result.hasServerSystemTimeEchoMsec;
+}
+- (UInt32) serverSystemTimeEchoMsec {
+  return result.serverSystemTimeEchoMsec;
+}
+- (ClockSyncEchoBuilder*) setServerSystemTimeEchoMsec:(UInt32) value {
+  result.hasServerSystemTimeEchoMsec = YES;
+  result.serverSystemTimeEchoMsec = value;
+  return self;
+}
+- (ClockSyncEchoBuilder*) clearServerSystemTimeEchoMsec {
+  result.hasServerSystemTimeEchoMsec = NO;
+  result.serverSystemTimeEchoMsec = 0;
+  return self;
+}
+- (BOOL) hasClientSystemTimeSec {
+  return result.hasClientSystemTimeSec;
+}
+- (UInt32) clientSystemTimeSec {
+  return result.clientSystemTimeSec;
+}
+- (ClockSyncEchoBuilder*) setClientSystemTimeSec:(UInt32) value {
+  result.hasClientSystemTimeSec = YES;
+  result.clientSystemTimeSec = value;
+  return self;
+}
+- (ClockSyncEchoBuilder*) clearClientSystemTimeSec {
+  result.hasClientSystemTimeSec = NO;
+  result.clientSystemTimeSec = 0;
+  return self;
+}
+- (BOOL) hasClientSystemTimeMsec {
+  return result.hasClientSystemTimeMsec;
+}
+- (UInt32) clientSystemTimeMsec {
+  return result.clientSystemTimeMsec;
+}
+- (ClockSyncEchoBuilder*) setClientSystemTimeMsec:(UInt32) value {
+  result.hasClientSystemTimeMsec = YES;
+  result.clientSystemTimeMsec = value;
+  return self;
+}
+- (ClockSyncEchoBuilder*) clearClientSystemTimeMsec {
+  result.hasClientSystemTimeMsec = NO;
+  result.clientSystemTimeMsec = 0;
+  return self;
+}
+@end
+
+@interface LatencyMeasure ()
+@property UInt64 earliestTime;
+@property UInt64 latestTime;
+@property UInt32 latencyRtpSequence;
+@property UInt32 latencyRtpSsrc;
+@end
+
+@implementation LatencyMeasure
+
+- (BOOL) hasEarliestTime {
+  return !!hasEarliestTime_;
+}
+- (void) setHasEarliestTime:(BOOL) value_ {
+  hasEarliestTime_ = !!value_;
+}
+@synthesize earliestTime;
+- (BOOL) hasLatestTime {
+  return !!hasLatestTime_;
+}
+- (void) setHasLatestTime:(BOOL) value_ {
+  hasLatestTime_ = !!value_;
+}
+@synthesize latestTime;
+- (BOOL) hasLatencyRtpSequence {
+  return !!hasLatencyRtpSequence_;
+}
+- (void) setHasLatencyRtpSequence:(BOOL) value_ {
+  hasLatencyRtpSequence_ = !!value_;
+}
+@synthesize latencyRtpSequence;
+- (BOOL) hasLatencyRtpSsrc {
+  return !!hasLatencyRtpSsrc_;
+}
+- (void) setHasLatencyRtpSsrc:(BOOL) value_ {
+  hasLatencyRtpSsrc_ = !!value_;
+}
+@synthesize latencyRtpSsrc;
+- (id) init {
+  if ((self = [super init])) {
+    self.earliestTime = 0L;
+    self.latestTime = 0L;
+    self.latencyRtpSequence = 0;
+    self.latencyRtpSsrc = 0;
+  }
+  return self;
+}
+static LatencyMeasure* defaultLatencyMeasureInstance = nil;
++ (void) initialize {
+  if (self == [LatencyMeasure class]) {
+    defaultLatencyMeasureInstance = [[LatencyMeasure alloc] init];
+  }
+}
++ (LatencyMeasure*) defaultInstance {
+  return defaultLatencyMeasureInstance;
+}
+- (LatencyMeasure*) defaultInstance {
+  return defaultLatencyMeasureInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasEarliestTime) {
+    [output writeUInt64:1 value:self.earliestTime];
+  }
+  if (self.hasLatestTime) {
+    [output writeUInt64:2 value:self.latestTime];
+  }
+  if (self.hasLatencyRtpSequence) {
+    [output writeUInt32:3 value:self.latencyRtpSequence];
+  }
+  if (self.hasLatencyRtpSsrc) {
+    [output writeUInt32:4 value:self.latencyRtpSsrc];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasEarliestTime) {
+    size_ += computeUInt64Size(1, self.earliestTime);
+  }
+  if (self.hasLatestTime) {
+    size_ += computeUInt64Size(2, self.latestTime);
+  }
+  if (self.hasLatencyRtpSequence) {
+    size_ += computeUInt32Size(3, self.latencyRtpSequence);
+  }
+  if (self.hasLatencyRtpSsrc) {
+    size_ += computeUInt32Size(4, self.latencyRtpSsrc);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (LatencyMeasure*) parseFromData:(NSData*) data {
+  return (LatencyMeasure*)[[[LatencyMeasure builder] mergeFromData:data] build];
+}
++ (LatencyMeasure*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (LatencyMeasure*)[[[LatencyMeasure builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (LatencyMeasure*) parseFromInputStream:(NSInputStream*) input {
+  return (LatencyMeasure*)[[[LatencyMeasure builder] mergeFromInputStream:input] build];
+}
++ (LatencyMeasure*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (LatencyMeasure*)[[[LatencyMeasure builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (LatencyMeasure*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (LatencyMeasure*)[[[LatencyMeasure builder] mergeFromCodedInputStream:input] build];
+}
++ (LatencyMeasure*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (LatencyMeasure*)[[[LatencyMeasure builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (LatencyMeasureBuilder*) builder {
+  return [[LatencyMeasureBuilder alloc] init];
+}
++ (LatencyMeasureBuilder*) builderWithPrototype:(LatencyMeasure*) prototype {
+  return [[LatencyMeasure builder] mergeFrom:prototype];
+}
+- (LatencyMeasureBuilder*) builder {
+  return [LatencyMeasure builder];
+}
+- (LatencyMeasureBuilder*) toBuilder {
+  return [LatencyMeasure builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasEarliestTime) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"earliestTime", [NSNumber numberWithLongLong:self.earliestTime]];
+  }
+  if (self.hasLatestTime) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"latestTime", [NSNumber numberWithLongLong:self.latestTime]];
+  }
+  if (self.hasLatencyRtpSequence) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"latencyRtpSequence", [NSNumber numberWithInteger:self.latencyRtpSequence]];
+  }
+  if (self.hasLatencyRtpSsrc) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"latencyRtpSsrc", [NSNumber numberWithInteger:self.latencyRtpSsrc]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[LatencyMeasure class]]) {
+    return NO;
+  }
+  LatencyMeasure *otherMessage = other;
+  return
+      self.hasEarliestTime == otherMessage.hasEarliestTime &&
+      (!self.hasEarliestTime || self.earliestTime == otherMessage.earliestTime) &&
+      self.hasLatestTime == otherMessage.hasLatestTime &&
+      (!self.hasLatestTime || self.latestTime == otherMessage.latestTime) &&
+      self.hasLatencyRtpSequence == otherMessage.hasLatencyRtpSequence &&
+      (!self.hasLatencyRtpSequence || self.latencyRtpSequence == otherMessage.latencyRtpSequence) &&
+      self.hasLatencyRtpSsrc == otherMessage.hasLatencyRtpSsrc &&
+      (!self.hasLatencyRtpSsrc || self.latencyRtpSsrc == otherMessage.latencyRtpSsrc) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasEarliestTime) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.earliestTime] hash];
+  }
+  if (self.hasLatestTime) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.latestTime] hash];
+  }
+  if (self.hasLatencyRtpSequence) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.latencyRtpSequence] hash];
+  }
+  if (self.hasLatencyRtpSsrc) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.latencyRtpSsrc] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface LatencyMeasureBuilder()
+@property (strong) LatencyMeasure* result;
+@end
+
+@implementation LatencyMeasureBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[LatencyMeasure alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (LatencyMeasureBuilder*) clear {
+  self.result = [[LatencyMeasure alloc] init];
+  return self;
+}
+- (LatencyMeasureBuilder*) clone {
+  return [LatencyMeasure builderWithPrototype:result];
+}
+- (LatencyMeasure*) defaultInstance {
+  return [LatencyMeasure defaultInstance];
+}
+- (LatencyMeasure*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (LatencyMeasure*) buildPartial {
+  LatencyMeasure* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (LatencyMeasureBuilder*) mergeFrom:(LatencyMeasure*) other {
+  if (other == [LatencyMeasure defaultInstance]) {
+    return self;
+  }
+  if (other.hasEarliestTime) {
+    [self setEarliestTime:other.earliestTime];
+  }
+  if (other.hasLatestTime) {
+    [self setLatestTime:other.latestTime];
+  }
+  if (other.hasLatencyRtpSequence) {
+    [self setLatencyRtpSequence:other.latencyRtpSequence];
+  }
+  if (other.hasLatencyRtpSsrc) {
+    [self setLatencyRtpSsrc:other.latencyRtpSsrc];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (LatencyMeasureBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (LatencyMeasureBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setEarliestTime:[input readUInt64]];
+        break;
+      }
+      case 16: {
+        [self setLatestTime:[input readUInt64]];
+        break;
+      }
+      case 24: {
+        [self setLatencyRtpSequence:[input readUInt32]];
+        break;
+      }
+      case 32: {
+        [self setLatencyRtpSsrc:[input readUInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasEarliestTime {
+  return result.hasEarliestTime;
+}
+- (UInt64) earliestTime {
+  return result.earliestTime;
+}
+- (LatencyMeasureBuilder*) setEarliestTime:(UInt64) value {
+  result.hasEarliestTime = YES;
+  result.earliestTime = value;
+  return self;
+}
+- (LatencyMeasureBuilder*) clearEarliestTime {
+  result.hasEarliestTime = NO;
+  result.earliestTime = 0L;
+  return self;
+}
+- (BOOL) hasLatestTime {
+  return result.hasLatestTime;
+}
+- (UInt64) latestTime {
+  return result.latestTime;
+}
+- (LatencyMeasureBuilder*) setLatestTime:(UInt64) value {
+  result.hasLatestTime = YES;
+  result.latestTime = value;
+  return self;
+}
+- (LatencyMeasureBuilder*) clearLatestTime {
+  result.hasLatestTime = NO;
+  result.latestTime = 0L;
+  return self;
+}
+- (BOOL) hasLatencyRtpSequence {
+  return result.hasLatencyRtpSequence;
+}
+- (UInt32) latencyRtpSequence {
+  return result.latencyRtpSequence;
+}
+- (LatencyMeasureBuilder*) setLatencyRtpSequence:(UInt32) value {
+  result.hasLatencyRtpSequence = YES;
+  result.latencyRtpSequence = value;
+  return self;
+}
+- (LatencyMeasureBuilder*) clearLatencyRtpSequence {
+  result.hasLatencyRtpSequence = NO;
+  result.latencyRtpSequence = 0;
+  return self;
+}
+- (BOOL) hasLatencyRtpSsrc {
+  return result.hasLatencyRtpSsrc;
+}
+- (UInt32) latencyRtpSsrc {
+  return result.latencyRtpSsrc;
+}
+- (LatencyMeasureBuilder*) setLatencyRtpSsrc:(UInt32) value {
+  result.hasLatencyRtpSsrc = YES;
+  result.latencyRtpSsrc = value;
+  return self;
+}
+- (LatencyMeasureBuilder*) clearLatencyRtpSsrc {
+  result.hasLatencyRtpSsrc = NO;
+  result.latencyRtpSsrc = 0;
+  return self;
+}
+@end
+
+@interface Redirect ()
+@property (strong) NS_RETURNS_NOT_RETAINED NSString* newHost;
+@end
+
+@implementation Redirect
+
+- (BOOL) hasNewHost {
+  return !!hasNewHost_;
+}
+- (void) setHasNewHost:(BOOL) value_ {
+  hasNewHost_ = !!value_;
+}
+@synthesize newHost;
+- (id) init {
+  if ((self = [super init])) {
+    self.newHost = @"";
+  }
+  return self;
+}
+static Redirect* defaultRedirectInstance = nil;
++ (void) initialize {
+  if (self == [Redirect class]) {
+    defaultRedirectInstance = [[Redirect alloc] init];
+  }
+}
++ (Redirect*) defaultInstance {
+  return defaultRedirectInstance;
+}
+- (Redirect*) defaultInstance {
+  return defaultRedirectInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasNewHost) {
+    [output writeString:1 value:self.newHost];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasNewHost) {
+    size_ += computeStringSize(1, self.newHost);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Redirect*) parseFromData:(NSData*) data {
+  return (Redirect*)[[[Redirect builder] mergeFromData:data] build];
+}
++ (Redirect*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Redirect*)[[[Redirect builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Redirect*) parseFromInputStream:(NSInputStream*) input {
+  return (Redirect*)[[[Redirect builder] mergeFromInputStream:input] build];
+}
++ (Redirect*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Redirect*)[[[Redirect builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Redirect*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Redirect*)[[[Redirect builder] mergeFromCodedInputStream:input] build];
+}
++ (Redirect*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Redirect*)[[[Redirect builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (RedirectBuilder*) builder {
+  return [[RedirectBuilder alloc] init];
+}
++ (RedirectBuilder*) builderWithPrototype:(Redirect*) prototype {
+  return [[Redirect builder] mergeFrom:prototype];
+}
+- (RedirectBuilder*) builder {
+  return [Redirect builder];
+}
+- (RedirectBuilder*) toBuilder {
+  return [Redirect builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasNewHost) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"newHost", self.newHost];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Redirect class]]) {
+    return NO;
+  }
+  Redirect *otherMessage = other;
+  return
+      self.hasNewHost == otherMessage.hasNewHost &&
+      (!self.hasNewHost || [self.newHost isEqual:otherMessage.newHost]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasNewHost) {
+    hashCode = hashCode * 31 + [self.newHost hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface RedirectBuilder()
+@property (strong) Redirect* result;
+@end
+
+@implementation RedirectBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Redirect alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (RedirectBuilder*) clear {
+  self.result = [[Redirect alloc] init];
+  return self;
+}
+- (RedirectBuilder*) clone {
+  return [Redirect builderWithPrototype:result];
+}
+- (Redirect*) defaultInstance {
+  return [Redirect defaultInstance];
+}
+- (Redirect*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Redirect*) buildPartial {
+  Redirect* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (RedirectBuilder*) mergeFrom:(Redirect*) other {
+  if (other == [Redirect defaultInstance]) {
+    return self;
+  }
+  if (other.hasNewHost) {
+    [self setNewHost:other.newHost];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (RedirectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (RedirectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setNewHost:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasNewHost {
+  return result.hasNewHost;
+}
+- (NSString*) newHost {
+  return result.newHost;
+}
+- (RedirectBuilder*) setNewHost:(NSString*) value {
+  result.hasNewHost = YES;
+  result.newHost = value;
+  return self;
+}
+- (RedirectBuilder*) clearNewHost {
+  result.hasNewHost = NO;
+  result.newHost = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Pair.pb.h b/src/gen_proto/Pair.pb.h
new file mode 100644
index 0000000..221b0b9
--- /dev/null
+++ b/src/gen_proto/Pair.pb.h
@@ -0,0 +1,87 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class Pair;
+@class PairBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+
+@interface PairRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface Pair : PBGeneratedMessage {
+@private
+  BOOL hasKey_:1;
+  BOOL hasValue_:1;
+  NSString* key;
+  NSString* value;
+}
+- (BOOL) hasKey;
+- (BOOL) hasValue;
+@property (readonly, strong) NSString* key;
+@property (readonly, strong) NSString* value;
+
++ (Pair*) defaultInstance;
+- (Pair*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PairBuilder*) builder;
++ (PairBuilder*) builder;
++ (PairBuilder*) builderWithPrototype:(Pair*) prototype;
+- (PairBuilder*) toBuilder;
+
++ (Pair*) parseFromData:(NSData*) data;
++ (Pair*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Pair*) parseFromInputStream:(NSInputStream*) input;
++ (Pair*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (Pair*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (Pair*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PairBuilder : PBGeneratedMessageBuilder {
+@private
+  Pair* result;
+}
+
+- (Pair*) defaultInstance;
+
+- (PairBuilder*) clear;
+- (PairBuilder*) clone;
+
+- (Pair*) build;
+- (Pair*) buildPartial;
+
+- (PairBuilder*) mergeFrom:(Pair*) other;
+- (PairBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PairBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasKey;
+- (NSString*) key;
+- (PairBuilder*) setKey:(NSString*) value;
+- (PairBuilder*) clearKey;
+
+- (BOOL) hasValue;
+- (NSString*) value;
+- (PairBuilder*) setValue:(NSString*) value;
+- (PairBuilder*) clearValue;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Pair.pb.m b/src/gen_proto/Pair.pb.m
new file mode 100644
index 0000000..8fc7f8e
--- /dev/null
+++ b/src/gen_proto/Pair.pb.m
@@ -0,0 +1,270 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Pair.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation PairRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [PairRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface Pair ()
+@property (strong) NSString* key;
+@property (strong) NSString* value;
+@end
+
+@implementation Pair
+
+- (BOOL) hasKey {
+  return !!hasKey_;
+}
+- (void) setHasKey:(BOOL) value_ {
+  hasKey_ = !!value_;
+}
+@synthesize key;
+- (BOOL) hasValue {
+  return !!hasValue_;
+}
+- (void) setHasValue:(BOOL) value_ {
+  hasValue_ = !!value_;
+}
+@synthesize value;
+- (id) init {
+  if ((self = [super init])) {
+    self.key = @"";
+    self.value = @"";
+  }
+  return self;
+}
+static Pair* defaultPairInstance = nil;
++ (void) initialize {
+  if (self == [Pair class]) {
+    defaultPairInstance = [[Pair alloc] init];
+  }
+}
++ (Pair*) defaultInstance {
+  return defaultPairInstance;
+}
+- (Pair*) defaultInstance {
+  return defaultPairInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasKey) {
+    [output writeString:1 value:self.key];
+  }
+  if (self.hasValue) {
+    [output writeString:2 value:self.value];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasKey) {
+    size_ += computeStringSize(1, self.key);
+  }
+  if (self.hasValue) {
+    size_ += computeStringSize(2, self.value);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (Pair*) parseFromData:(NSData*) data {
+  return (Pair*)[[[Pair builder] mergeFromData:data] build];
+}
++ (Pair*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Pair*)[[[Pair builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (Pair*) parseFromInputStream:(NSInputStream*) input {
+  return (Pair*)[[[Pair builder] mergeFromInputStream:input] build];
+}
++ (Pair*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Pair*)[[[Pair builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (Pair*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (Pair*)[[[Pair builder] mergeFromCodedInputStream:input] build];
+}
++ (Pair*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (Pair*)[[[Pair builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PairBuilder*) builder {
+  return [[PairBuilder alloc] init];
+}
++ (PairBuilder*) builderWithPrototype:(Pair*) prototype {
+  return [[Pair builder] mergeFrom:prototype];
+}
+- (PairBuilder*) builder {
+  return [Pair builder];
+}
+- (PairBuilder*) toBuilder {
+  return [Pair builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasKey) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"key", self.key];
+  }
+  if (self.hasValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"value", self.value];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[Pair class]]) {
+    return NO;
+  }
+  Pair *otherMessage = other;
+  return
+      self.hasKey == otherMessage.hasKey &&
+      (!self.hasKey || [self.key isEqual:otherMessage.key]) &&
+      self.hasValue == otherMessage.hasValue &&
+      (!self.hasValue || [self.value isEqual:otherMessage.value]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasKey) {
+    hashCode = hashCode * 31 + [self.key hash];
+  }
+  if (self.hasValue) {
+    hashCode = hashCode * 31 + [self.value hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PairBuilder()
+@property (strong) Pair* result;
+@end
+
+@implementation PairBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[Pair alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PairBuilder*) clear {
+  self.result = [[Pair alloc] init];
+  return self;
+}
+- (PairBuilder*) clone {
+  return [Pair builderWithPrototype:result];
+}
+- (Pair*) defaultInstance {
+  return [Pair defaultInstance];
+}
+- (Pair*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (Pair*) buildPartial {
+  Pair* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PairBuilder*) mergeFrom:(Pair*) other {
+  if (other == [Pair defaultInstance]) {
+    return self;
+  }
+  if (other.hasKey) {
+    [self setKey:other.key];
+  }
+  if (other.hasValue) {
+    [self setValue:other.value];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PairBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PairBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setKey:[input readString]];
+        break;
+      }
+      case 18: {
+        [self setValue:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasKey {
+  return result.hasKey;
+}
+- (NSString*) key {
+  return result.key;
+}
+- (PairBuilder*) setKey:(NSString*) value {
+  result.hasKey = YES;
+  result.key = value;
+  return self;
+}
+- (PairBuilder*) clearKey {
+  result.hasKey = NO;
+  result.key = @"";
+  return self;
+}
+- (BOOL) hasValue {
+  return result.hasValue;
+}
+- (NSString*) value {
+  return result.value;
+}
+- (PairBuilder*) setValue:(NSString*) value {
+  result.hasValue = YES;
+  result.value = value;
+  return self;
+}
+- (PairBuilder*) clearValue {
+  result.hasValue = NO;
+  result.value = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Scrubbytalk.pb.h b/src/gen_proto/Scrubbytalk.pb.h
new file mode 100644
index 0000000..fe5c3d9
--- /dev/null
+++ b/src/gen_proto/Scrubbytalk.pb.h
@@ -0,0 +1,271 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class ScrubbytalkMessage;
+@class ScrubbytalkMessageBuilder;
+@class VideoFrameV2;
+@class VideoFrameV2Builder;
+@class VideoFrameV3;
+@class VideoFrameV3Builder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  ScrubbytalkMessageMsgTypeVideoFrame = 1,
+} ScrubbytalkMessageMsgType;
+
+BOOL ScrubbytalkMessageMsgTypeIsValidValue(ScrubbytalkMessageMsgType value);
+
+
+@interface ScrubbytalkRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface ScrubbytalkMessage : PBGeneratedMessage {
+@private
+  BOOL hasVideoFrameV2_:1;
+  BOOL hasVideoFrameV3_:1;
+  BOOL hasMsgType_:1;
+  VideoFrameV2* videoFrameV2;
+  VideoFrameV3* videoFrameV3;
+  ScrubbytalkMessageMsgType msgType;
+}
+- (BOOL) hasMsgType;
+- (BOOL) hasVideoFrameV2;
+- (BOOL) hasVideoFrameV3;
+@property (readonly) ScrubbytalkMessageMsgType msgType;
+@property (readonly, strong) VideoFrameV2* videoFrameV2;
+@property (readonly, strong) VideoFrameV3* videoFrameV3;
+
++ (ScrubbytalkMessage*) defaultInstance;
+- (ScrubbytalkMessage*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ScrubbytalkMessageBuilder*) builder;
++ (ScrubbytalkMessageBuilder*) builder;
++ (ScrubbytalkMessageBuilder*) builderWithPrototype:(ScrubbytalkMessage*) prototype;
+- (ScrubbytalkMessageBuilder*) toBuilder;
+
++ (ScrubbytalkMessage*) parseFromData:(NSData*) data;
++ (ScrubbytalkMessage*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ScrubbytalkMessage*) parseFromInputStream:(NSInputStream*) input;
++ (ScrubbytalkMessage*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ScrubbytalkMessage*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ScrubbytalkMessage*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ScrubbytalkMessageBuilder : PBGeneratedMessageBuilder {
+@private
+  ScrubbytalkMessage* result;
+}
+
+- (ScrubbytalkMessage*) defaultInstance;
+
+- (ScrubbytalkMessageBuilder*) clear;
+- (ScrubbytalkMessageBuilder*) clone;
+
+- (ScrubbytalkMessage*) build;
+- (ScrubbytalkMessage*) buildPartial;
+
+- (ScrubbytalkMessageBuilder*) mergeFrom:(ScrubbytalkMessage*) other;
+- (ScrubbytalkMessageBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ScrubbytalkMessageBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasMsgType;
+- (ScrubbytalkMessageMsgType) msgType;
+- (ScrubbytalkMessageBuilder*) setMsgType:(ScrubbytalkMessageMsgType) value;
+- (ScrubbytalkMessageBuilder*) clearMsgType;
+
+- (BOOL) hasVideoFrameV2;
+- (VideoFrameV2*) videoFrameV2;
+- (ScrubbytalkMessageBuilder*) setVideoFrameV2:(VideoFrameV2*) value;
+- (ScrubbytalkMessageBuilder*) setVideoFrameV2Builder:(VideoFrameV2Builder*) builderForValue;
+- (ScrubbytalkMessageBuilder*) mergeVideoFrameV2:(VideoFrameV2*) value;
+- (ScrubbytalkMessageBuilder*) clearVideoFrameV2;
+
+- (BOOL) hasVideoFrameV3;
+- (VideoFrameV3*) videoFrameV3;
+- (ScrubbytalkMessageBuilder*) setVideoFrameV3:(VideoFrameV3*) value;
+- (ScrubbytalkMessageBuilder*) setVideoFrameV3Builder:(VideoFrameV3Builder*) builderForValue;
+- (ScrubbytalkMessageBuilder*) mergeVideoFrameV3:(VideoFrameV3*) value;
+- (ScrubbytalkMessageBuilder*) clearVideoFrameV3;
+@end
+
+@interface VideoFrameV2 : PBGeneratedMessage {
+@private
+  BOOL hasIsCacheable_:1;
+  BOOL hasIsLastChunkFrame_:1;
+  BOOL hasTimestamp_:1;
+  BOOL hasChunkNum_:1;
+  BOOL isCacheable_:1;
+  BOOL isLastChunkFrame_:1;
+  Float64 timestamp;
+  SInt64 chunkNum;
+  NSMutableArray * nalsArray;
+}
+- (BOOL) hasTimestamp;
+- (BOOL) hasChunkNum;
+- (BOOL) hasIsCacheable;
+- (BOOL) hasIsLastChunkFrame;
+@property (readonly, strong) PBArray * nals;
+@property (readonly) Float64 timestamp;
+@property (readonly) SInt64 chunkNum;
+- (BOOL) isCacheable;
+- (BOOL) isLastChunkFrame;
+- (NSData*)nalsAtIndex:(NSUInteger)index;
+
++ (VideoFrameV2*) defaultInstance;
+- (VideoFrameV2*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (VideoFrameV2Builder*) builder;
++ (VideoFrameV2Builder*) builder;
++ (VideoFrameV2Builder*) builderWithPrototype:(VideoFrameV2*) prototype;
+- (VideoFrameV2Builder*) toBuilder;
+
++ (VideoFrameV2*) parseFromData:(NSData*) data;
++ (VideoFrameV2*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (VideoFrameV2*) parseFromInputStream:(NSInputStream*) input;
++ (VideoFrameV2*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (VideoFrameV2*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (VideoFrameV2*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface VideoFrameV2Builder : PBGeneratedMessageBuilder {
+@private
+  VideoFrameV2* result;
+}
+
+- (VideoFrameV2*) defaultInstance;
+
+- (VideoFrameV2Builder*) clear;
+- (VideoFrameV2Builder*) clone;
+
+- (VideoFrameV2*) build;
+- (VideoFrameV2*) buildPartial;
+
+- (VideoFrameV2Builder*) mergeFrom:(VideoFrameV2*) other;
+- (VideoFrameV2Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (VideoFrameV2Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (NSMutableArray *)nals;
+- (NSData*)nalsAtIndex:(NSUInteger)index;
+- (VideoFrameV2Builder *)addNals:(NSData*)value;
+- (VideoFrameV2Builder *)setNalsArray:(NSArray *)array;
+- (VideoFrameV2Builder *)clearNals;
+
+- (BOOL) hasTimestamp;
+- (Float64) timestamp;
+- (VideoFrameV2Builder*) setTimestamp:(Float64) value;
+- (VideoFrameV2Builder*) clearTimestamp;
+
+- (BOOL) hasChunkNum;
+- (SInt64) chunkNum;
+- (VideoFrameV2Builder*) setChunkNum:(SInt64) value;
+- (VideoFrameV2Builder*) clearChunkNum;
+
+- (BOOL) hasIsCacheable;
+- (BOOL) isCacheable;
+- (VideoFrameV2Builder*) setIsCacheable:(BOOL) value;
+- (VideoFrameV2Builder*) clearIsCacheable;
+
+- (BOOL) hasIsLastChunkFrame;
+- (BOOL) isLastChunkFrame;
+- (VideoFrameV2Builder*) setIsLastChunkFrame:(BOOL) value;
+- (VideoFrameV2Builder*) clearIsLastChunkFrame;
+@end
+
+@interface VideoFrameV3 : PBGeneratedMessage {
+@private
+  BOOL hasTimestamp_:1;
+  BOOL hasChunkStartTime_:1;
+  BOOL hasCacheToken_:1;
+  Float64 timestamp;
+  Float64 chunkStartTime;
+  NSString* cacheToken;
+  NSMutableArray * nalsArray;
+}
+- (BOOL) hasTimestamp;
+- (BOOL) hasCacheToken;
+- (BOOL) hasChunkStartTime;
+@property (readonly, strong) PBArray * nals;
+@property (readonly) Float64 timestamp;
+@property (readonly, strong) NSString* cacheToken;
+@property (readonly) Float64 chunkStartTime;
+- (NSData*)nalsAtIndex:(NSUInteger)index;
+
++ (VideoFrameV3*) defaultInstance;
+- (VideoFrameV3*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (VideoFrameV3Builder*) builder;
++ (VideoFrameV3Builder*) builder;
++ (VideoFrameV3Builder*) builderWithPrototype:(VideoFrameV3*) prototype;
+- (VideoFrameV3Builder*) toBuilder;
+
++ (VideoFrameV3*) parseFromData:(NSData*) data;
++ (VideoFrameV3*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (VideoFrameV3*) parseFromInputStream:(NSInputStream*) input;
++ (VideoFrameV3*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (VideoFrameV3*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (VideoFrameV3*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface VideoFrameV3Builder : PBGeneratedMessageBuilder {
+@private
+  VideoFrameV3* result;
+}
+
+- (VideoFrameV3*) defaultInstance;
+
+- (VideoFrameV3Builder*) clear;
+- (VideoFrameV3Builder*) clone;
+
+- (VideoFrameV3*) build;
+- (VideoFrameV3*) buildPartial;
+
+- (VideoFrameV3Builder*) mergeFrom:(VideoFrameV3*) other;
+- (VideoFrameV3Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (VideoFrameV3Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (NSMutableArray *)nals;
+- (NSData*)nalsAtIndex:(NSUInteger)index;
+- (VideoFrameV3Builder *)addNals:(NSData*)value;
+- (VideoFrameV3Builder *)setNalsArray:(NSArray *)array;
+- (VideoFrameV3Builder *)clearNals;
+
+- (BOOL) hasTimestamp;
+- (Float64) timestamp;
+- (VideoFrameV3Builder*) setTimestamp:(Float64) value;
+- (VideoFrameV3Builder*) clearTimestamp;
+
+- (BOOL) hasCacheToken;
+- (NSString*) cacheToken;
+- (VideoFrameV3Builder*) setCacheToken:(NSString*) value;
+- (VideoFrameV3Builder*) clearCacheToken;
+
+- (BOOL) hasChunkStartTime;
+- (Float64) chunkStartTime;
+- (VideoFrameV3Builder*) setChunkStartTime:(Float64) value;
+- (VideoFrameV3Builder*) clearChunkStartTime;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Scrubbytalk.pb.m b/src/gen_proto/Scrubbytalk.pb.m
new file mode 100644
index 0000000..c411314
--- /dev/null
+++ b/src/gen_proto/Scrubbytalk.pb.m
@@ -0,0 +1,1136 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Scrubbytalk.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation ScrubbytalkRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [ScrubbytalkRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface ScrubbytalkMessage ()
+@property ScrubbytalkMessageMsgType msgType;
+@property (strong) VideoFrameV2* videoFrameV2;
+@property (strong) VideoFrameV3* videoFrameV3;
+@end
+
+@implementation ScrubbytalkMessage
+
+- (BOOL) hasMsgType {
+  return !!hasMsgType_;
+}
+- (void) setHasMsgType:(BOOL) value_ {
+  hasMsgType_ = !!value_;
+}
+@synthesize msgType;
+- (BOOL) hasVideoFrameV2 {
+  return !!hasVideoFrameV2_;
+}
+- (void) setHasVideoFrameV2:(BOOL) value_ {
+  hasVideoFrameV2_ = !!value_;
+}
+@synthesize videoFrameV2;
+- (BOOL) hasVideoFrameV3 {
+  return !!hasVideoFrameV3_;
+}
+- (void) setHasVideoFrameV3:(BOOL) value_ {
+  hasVideoFrameV3_ = !!value_;
+}
+@synthesize videoFrameV3;
+- (id) init {
+  if ((self = [super init])) {
+    self.msgType = ScrubbytalkMessageMsgTypeVideoFrame;
+    self.videoFrameV2 = [VideoFrameV2 defaultInstance];
+    self.videoFrameV3 = [VideoFrameV3 defaultInstance];
+  }
+  return self;
+}
+static ScrubbytalkMessage* defaultScrubbytalkMessageInstance = nil;
++ (void) initialize {
+  if (self == [ScrubbytalkMessage class]) {
+    defaultScrubbytalkMessageInstance = [[ScrubbytalkMessage alloc] init];
+  }
+}
++ (ScrubbytalkMessage*) defaultInstance {
+  return defaultScrubbytalkMessageInstance;
+}
+- (ScrubbytalkMessage*) defaultInstance {
+  return defaultScrubbytalkMessageInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasMsgType) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasMsgType) {
+    [output writeEnum:1 value:self.msgType];
+  }
+  if (self.hasVideoFrameV2) {
+    [output writeMessage:2 value:self.videoFrameV2];
+  }
+  if (self.hasVideoFrameV3) {
+    [output writeMessage:3 value:self.videoFrameV3];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasMsgType) {
+    size_ += computeEnumSize(1, self.msgType);
+  }
+  if (self.hasVideoFrameV2) {
+    size_ += computeMessageSize(2, self.videoFrameV2);
+  }
+  if (self.hasVideoFrameV3) {
+    size_ += computeMessageSize(3, self.videoFrameV3);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ScrubbytalkMessage*) parseFromData:(NSData*) data {
+  return (ScrubbytalkMessage*)[[[ScrubbytalkMessage builder] mergeFromData:data] build];
+}
++ (ScrubbytalkMessage*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ScrubbytalkMessage*)[[[ScrubbytalkMessage builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ScrubbytalkMessage*) parseFromInputStream:(NSInputStream*) input {
+  return (ScrubbytalkMessage*)[[[ScrubbytalkMessage builder] mergeFromInputStream:input] build];
+}
++ (ScrubbytalkMessage*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ScrubbytalkMessage*)[[[ScrubbytalkMessage builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ScrubbytalkMessage*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ScrubbytalkMessage*)[[[ScrubbytalkMessage builder] mergeFromCodedInputStream:input] build];
+}
++ (ScrubbytalkMessage*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ScrubbytalkMessage*)[[[ScrubbytalkMessage builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ScrubbytalkMessageBuilder*) builder {
+  return [[ScrubbytalkMessageBuilder alloc] init];
+}
++ (ScrubbytalkMessageBuilder*) builderWithPrototype:(ScrubbytalkMessage*) prototype {
+  return [[ScrubbytalkMessage builder] mergeFrom:prototype];
+}
+- (ScrubbytalkMessageBuilder*) builder {
+  return [ScrubbytalkMessage builder];
+}
+- (ScrubbytalkMessageBuilder*) toBuilder {
+  return [ScrubbytalkMessage builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasMsgType) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"msgType", self.msgType];
+  }
+  if (self.hasVideoFrameV2) {
+    [output appendFormat:@"%@%@ {\n", indent, @"videoFrameV2"];
+    [self.videoFrameV2 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasVideoFrameV3) {
+    [output appendFormat:@"%@%@ {\n", indent, @"videoFrameV3"];
+    [self.videoFrameV3 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ScrubbytalkMessage class]]) {
+    return NO;
+  }
+  ScrubbytalkMessage *otherMessage = other;
+  return
+      self.hasMsgType == otherMessage.hasMsgType &&
+      (!self.hasMsgType || self.msgType == otherMessage.msgType) &&
+      self.hasVideoFrameV2 == otherMessage.hasVideoFrameV2 &&
+      (!self.hasVideoFrameV2 || [self.videoFrameV2 isEqual:otherMessage.videoFrameV2]) &&
+      self.hasVideoFrameV3 == otherMessage.hasVideoFrameV3 &&
+      (!self.hasVideoFrameV3 || [self.videoFrameV3 isEqual:otherMessage.videoFrameV3]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasMsgType) {
+    hashCode = hashCode * 31 + self.msgType;
+  }
+  if (self.hasVideoFrameV2) {
+    hashCode = hashCode * 31 + [self.videoFrameV2 hash];
+  }
+  if (self.hasVideoFrameV3) {
+    hashCode = hashCode * 31 + [self.videoFrameV3 hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL ScrubbytalkMessageMsgTypeIsValidValue(ScrubbytalkMessageMsgType value) {
+  switch (value) {
+    case ScrubbytalkMessageMsgTypeVideoFrame:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface ScrubbytalkMessageBuilder()
+@property (strong) ScrubbytalkMessage* result;
+@end
+
+@implementation ScrubbytalkMessageBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ScrubbytalkMessage alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ScrubbytalkMessageBuilder*) clear {
+  self.result = [[ScrubbytalkMessage alloc] init];
+  return self;
+}
+- (ScrubbytalkMessageBuilder*) clone {
+  return [ScrubbytalkMessage builderWithPrototype:result];
+}
+- (ScrubbytalkMessage*) defaultInstance {
+  return [ScrubbytalkMessage defaultInstance];
+}
+- (ScrubbytalkMessage*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ScrubbytalkMessage*) buildPartial {
+  ScrubbytalkMessage* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ScrubbytalkMessageBuilder*) mergeFrom:(ScrubbytalkMessage*) other {
+  if (other == [ScrubbytalkMessage defaultInstance]) {
+    return self;
+  }
+  if (other.hasMsgType) {
+    [self setMsgType:other.msgType];
+  }
+  if (other.hasVideoFrameV2) {
+    [self mergeVideoFrameV2:other.videoFrameV2];
+  }
+  if (other.hasVideoFrameV3) {
+    [self mergeVideoFrameV3:other.videoFrameV3];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ScrubbytalkMessageBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ScrubbytalkMessageBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        ScrubbytalkMessageMsgType value = (ScrubbytalkMessageMsgType)[input readEnum];
+        if (ScrubbytalkMessageMsgTypeIsValidValue(value)) {
+          [self setMsgType:value];
+        } else {
+          [unknownFields mergeVarintField:1 value:value];
+        }
+        break;
+      }
+      case 18: {
+        VideoFrameV2Builder* subBuilder = [VideoFrameV2 builder];
+        if (self.hasVideoFrameV2) {
+          [subBuilder mergeFrom:self.videoFrameV2];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setVideoFrameV2:[subBuilder buildPartial]];
+        break;
+      }
+      case 26: {
+        VideoFrameV3Builder* subBuilder = [VideoFrameV3 builder];
+        if (self.hasVideoFrameV3) {
+          [subBuilder mergeFrom:self.videoFrameV3];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setVideoFrameV3:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasMsgType {
+  return result.hasMsgType;
+}
+- (ScrubbytalkMessageMsgType) msgType {
+  return result.msgType;
+}
+- (ScrubbytalkMessageBuilder*) setMsgType:(ScrubbytalkMessageMsgType) value {
+  result.hasMsgType = YES;
+  result.msgType = value;
+  return self;
+}
+- (ScrubbytalkMessageBuilder*) clearMsgType {
+  result.hasMsgType = NO;
+  result.msgType = ScrubbytalkMessageMsgTypeVideoFrame;
+  return self;
+}
+- (BOOL) hasVideoFrameV2 {
+  return result.hasVideoFrameV2;
+}
+- (VideoFrameV2*) videoFrameV2 {
+  return result.videoFrameV2;
+}
+- (ScrubbytalkMessageBuilder*) setVideoFrameV2:(VideoFrameV2*) value {
+  result.hasVideoFrameV2 = YES;
+  result.videoFrameV2 = value;
+  return self;
+}
+- (ScrubbytalkMessageBuilder*) setVideoFrameV2Builder:(VideoFrameV2Builder*) builderForValue {
+  return [self setVideoFrameV2:[builderForValue build]];
+}
+- (ScrubbytalkMessageBuilder*) mergeVideoFrameV2:(VideoFrameV2*) value {
+  if (result.hasVideoFrameV2 &&
+      result.videoFrameV2 != [VideoFrameV2 defaultInstance]) {
+    result.videoFrameV2 =
+      [[[VideoFrameV2 builderWithPrototype:result.videoFrameV2] mergeFrom:value] buildPartial];
+  } else {
+    result.videoFrameV2 = value;
+  }
+  result.hasVideoFrameV2 = YES;
+  return self;
+}
+- (ScrubbytalkMessageBuilder*) clearVideoFrameV2 {
+  result.hasVideoFrameV2 = NO;
+  result.videoFrameV2 = [VideoFrameV2 defaultInstance];
+  return self;
+}
+- (BOOL) hasVideoFrameV3 {
+  return result.hasVideoFrameV3;
+}
+- (VideoFrameV3*) videoFrameV3 {
+  return result.videoFrameV3;
+}
+- (ScrubbytalkMessageBuilder*) setVideoFrameV3:(VideoFrameV3*) value {
+  result.hasVideoFrameV3 = YES;
+  result.videoFrameV3 = value;
+  return self;
+}
+- (ScrubbytalkMessageBuilder*) setVideoFrameV3Builder:(VideoFrameV3Builder*) builderForValue {
+  return [self setVideoFrameV3:[builderForValue build]];
+}
+- (ScrubbytalkMessageBuilder*) mergeVideoFrameV3:(VideoFrameV3*) value {
+  if (result.hasVideoFrameV3 &&
+      result.videoFrameV3 != [VideoFrameV3 defaultInstance]) {
+    result.videoFrameV3 =
+      [[[VideoFrameV3 builderWithPrototype:result.videoFrameV3] mergeFrom:value] buildPartial];
+  } else {
+    result.videoFrameV3 = value;
+  }
+  result.hasVideoFrameV3 = YES;
+  return self;
+}
+- (ScrubbytalkMessageBuilder*) clearVideoFrameV3 {
+  result.hasVideoFrameV3 = NO;
+  result.videoFrameV3 = [VideoFrameV3 defaultInstance];
+  return self;
+}
+@end
+
+@interface VideoFrameV2 ()
+@property (strong) NSMutableArray * nalsArray;
+@property Float64 timestamp;
+@property SInt64 chunkNum;
+@property BOOL isCacheable;
+@property BOOL isLastChunkFrame;
+@end
+
+@implementation VideoFrameV2
+
+@synthesize nalsArray;
+@dynamic nals;
+- (BOOL) hasTimestamp {
+  return !!hasTimestamp_;
+}
+- (void) setHasTimestamp:(BOOL) value_ {
+  hasTimestamp_ = !!value_;
+}
+@synthesize timestamp;
+- (BOOL) hasChunkNum {
+  return !!hasChunkNum_;
+}
+- (void) setHasChunkNum:(BOOL) value_ {
+  hasChunkNum_ = !!value_;
+}
+@synthesize chunkNum;
+- (BOOL) hasIsCacheable {
+  return !!hasIsCacheable_;
+}
+- (void) setHasIsCacheable:(BOOL) value_ {
+  hasIsCacheable_ = !!value_;
+}
+- (BOOL) isCacheable {
+  return !!isCacheable_;
+}
+- (void) setIsCacheable:(BOOL) value_ {
+  isCacheable_ = !!value_;
+}
+- (BOOL) hasIsLastChunkFrame {
+  return !!hasIsLastChunkFrame_;
+}
+- (void) setHasIsLastChunkFrame:(BOOL) value_ {
+  hasIsLastChunkFrame_ = !!value_;
+}
+- (BOOL) isLastChunkFrame {
+  return !!isLastChunkFrame_;
+}
+- (void) setIsLastChunkFrame:(BOOL) value_ {
+  isLastChunkFrame_ = !!value_;
+}
+- (id) init {
+  if ((self = [super init])) {
+    self.timestamp = 0;
+    self.chunkNum = 0L;
+    self.isCacheable = NO;
+    self.isLastChunkFrame = NO;
+  }
+  return self;
+}
+static VideoFrameV2* defaultVideoFrameV2Instance = nil;
++ (void) initialize {
+  if (self == [VideoFrameV2 class]) {
+    defaultVideoFrameV2Instance = [[VideoFrameV2 alloc] init];
+  }
+}
++ (VideoFrameV2*) defaultInstance {
+  return defaultVideoFrameV2Instance;
+}
+- (VideoFrameV2*) defaultInstance {
+  return defaultVideoFrameV2Instance;
+}
+- (NSArray *)nals {
+  return nalsArray;
+}
+- (NSData*)nalsAtIndex:(NSUInteger)index {
+  return [nalsArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  [self.nalsArray enumerateObjectsUsingBlock:^(NSData *element, NSUInteger idx, BOOL *stop) {
+    [output writeData:1 value:element];
+  }];
+  if (self.hasTimestamp) {
+    [output writeDouble:2 value:self.timestamp];
+  }
+  if (self.hasChunkNum) {
+    [output writeInt64:3 value:self.chunkNum];
+  }
+  if (self.hasIsCacheable) {
+    [output writeBool:4 value:self.isCacheable];
+  }
+  if (self.hasIsLastChunkFrame) {
+    [output writeBool:5 value:self.isLastChunkFrame];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.nalsArray.count;
+    [self.nalsArray enumerateObjectsUsingBlock:^(NSData *element, NSUInteger idx, BOOL *stop) {
+      dataSize += computeDataSizeNoTag(element);
+    }];
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  if (self.hasTimestamp) {
+    size_ += computeDoubleSize(2, self.timestamp);
+  }
+  if (self.hasChunkNum) {
+    size_ += computeInt64Size(3, self.chunkNum);
+  }
+  if (self.hasIsCacheable) {
+    size_ += computeBoolSize(4, self.isCacheable);
+  }
+  if (self.hasIsLastChunkFrame) {
+    size_ += computeBoolSize(5, self.isLastChunkFrame);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (VideoFrameV2*) parseFromData:(NSData*) data {
+  return (VideoFrameV2*)[[[VideoFrameV2 builder] mergeFromData:data] build];
+}
++ (VideoFrameV2*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (VideoFrameV2*)[[[VideoFrameV2 builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (VideoFrameV2*) parseFromInputStream:(NSInputStream*) input {
+  return (VideoFrameV2*)[[[VideoFrameV2 builder] mergeFromInputStream:input] build];
+}
++ (VideoFrameV2*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (VideoFrameV2*)[[[VideoFrameV2 builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (VideoFrameV2*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (VideoFrameV2*)[[[VideoFrameV2 builder] mergeFromCodedInputStream:input] build];
+}
++ (VideoFrameV2*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (VideoFrameV2*)[[[VideoFrameV2 builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (VideoFrameV2Builder*) builder {
+  return [[VideoFrameV2Builder alloc] init];
+}
++ (VideoFrameV2Builder*) builderWithPrototype:(VideoFrameV2*) prototype {
+  return [[VideoFrameV2 builder] mergeFrom:prototype];
+}
+- (VideoFrameV2Builder*) builder {
+  return [VideoFrameV2 builder];
+}
+- (VideoFrameV2Builder*) toBuilder {
+  return [VideoFrameV2 builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.nalsArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"nals", obj];
+  }];
+  if (self.hasTimestamp) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"timestamp", [NSNumber numberWithDouble:self.timestamp]];
+  }
+  if (self.hasChunkNum) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"chunkNum", [NSNumber numberWithLongLong:self.chunkNum]];
+  }
+  if (self.hasIsCacheable) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"isCacheable", [NSNumber numberWithBool:self.isCacheable]];
+  }
+  if (self.hasIsLastChunkFrame) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"isLastChunkFrame", [NSNumber numberWithBool:self.isLastChunkFrame]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[VideoFrameV2 class]]) {
+    return NO;
+  }
+  VideoFrameV2 *otherMessage = other;
+  return
+      [self.nalsArray isEqualToArray:otherMessage.nalsArray] &&
+      self.hasTimestamp == otherMessage.hasTimestamp &&
+      (!self.hasTimestamp || self.timestamp == otherMessage.timestamp) &&
+      self.hasChunkNum == otherMessage.hasChunkNum &&
+      (!self.hasChunkNum || self.chunkNum == otherMessage.chunkNum) &&
+      self.hasIsCacheable == otherMessage.hasIsCacheable &&
+      (!self.hasIsCacheable || self.isCacheable == otherMessage.isCacheable) &&
+      self.hasIsLastChunkFrame == otherMessage.hasIsLastChunkFrame &&
+      (!self.hasIsLastChunkFrame || self.isLastChunkFrame == otherMessage.isLastChunkFrame) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  [self.nalsArray enumerateObjectsUsingBlock:^(id element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasTimestamp) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithDouble:self.timestamp] hash];
+  }
+  if (self.hasChunkNum) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.chunkNum] hash];
+  }
+  if (self.hasIsCacheable) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.isCacheable] hash];
+  }
+  if (self.hasIsLastChunkFrame) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.isLastChunkFrame] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface VideoFrameV2Builder()
+@property (strong) VideoFrameV2* result;
+@end
+
+@implementation VideoFrameV2Builder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[VideoFrameV2 alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (VideoFrameV2Builder*) clear {
+  self.result = [[VideoFrameV2 alloc] init];
+  return self;
+}
+- (VideoFrameV2Builder*) clone {
+  return [VideoFrameV2 builderWithPrototype:result];
+}
+- (VideoFrameV2*) defaultInstance {
+  return [VideoFrameV2 defaultInstance];
+}
+- (VideoFrameV2*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (VideoFrameV2*) buildPartial {
+  VideoFrameV2* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (VideoFrameV2Builder*) mergeFrom:(VideoFrameV2*) other {
+  if (other == [VideoFrameV2 defaultInstance]) {
+    return self;
+  }
+  if (other.nalsArray.count > 0) {
+    if (result.nalsArray == nil) {
+      result.nalsArray = [[NSMutableArray alloc] initWithArray:other.nalsArray];
+    } else {
+      [result.nalsArray addObjectsFromArray:other.nalsArray];
+    }
+  }
+  if (other.hasTimestamp) {
+    [self setTimestamp:other.timestamp];
+  }
+  if (other.hasChunkNum) {
+    [self setChunkNum:other.chunkNum];
+  }
+  if (other.hasIsCacheable) {
+    [self setIsCacheable:other.isCacheable];
+  }
+  if (other.hasIsLastChunkFrame) {
+    [self setIsLastChunkFrame:other.isLastChunkFrame];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (VideoFrameV2Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (VideoFrameV2Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self addNals:[input readData]];
+        break;
+      }
+      case 17: {
+        [self setTimestamp:[input readDouble]];
+        break;
+      }
+      case 24: {
+        [self setChunkNum:[input readInt64]];
+        break;
+      }
+      case 32: {
+        [self setIsCacheable:[input readBool]];
+        break;
+      }
+      case 40: {
+        [self setIsLastChunkFrame:[input readBool]];
+        break;
+      }
+    }
+  }
+}
+- (NSMutableArray *)nals {
+  return result.nalsArray;
+}
+- (NSData*)nalsAtIndex:(NSUInteger)index {
+  return [result nalsAtIndex:index];
+}
+- (VideoFrameV2Builder *)addNals:(NSData*)value {
+  if (result.nalsArray == nil) {
+    result.nalsArray = [[NSMutableArray alloc]init];
+  }
+  [result.nalsArray addObject:value];
+  return self;
+}
+- (VideoFrameV2Builder *)setNalsArray:(NSArray *)array {
+  result.nalsArray = [[NSMutableArray alloc] initWithArray:array];
+  return self;
+}
+- (VideoFrameV2Builder *)clearNals {
+  result.nalsArray = nil;
+  return self;
+}
+- (BOOL) hasTimestamp {
+  return result.hasTimestamp;
+}
+- (Float64) timestamp {
+  return result.timestamp;
+}
+- (VideoFrameV2Builder*) setTimestamp:(Float64) value {
+  result.hasTimestamp = YES;
+  result.timestamp = value;
+  return self;
+}
+- (VideoFrameV2Builder*) clearTimestamp {
+  result.hasTimestamp = NO;
+  result.timestamp = 0;
+  return self;
+}
+- (BOOL) hasChunkNum {
+  return result.hasChunkNum;
+}
+- (SInt64) chunkNum {
+  return result.chunkNum;
+}
+- (VideoFrameV2Builder*) setChunkNum:(SInt64) value {
+  result.hasChunkNum = YES;
+  result.chunkNum = value;
+  return self;
+}
+- (VideoFrameV2Builder*) clearChunkNum {
+  result.hasChunkNum = NO;
+  result.chunkNum = 0L;
+  return self;
+}
+- (BOOL) hasIsCacheable {
+  return result.hasIsCacheable;
+}
+- (BOOL) isCacheable {
+  return result.isCacheable;
+}
+- (VideoFrameV2Builder*) setIsCacheable:(BOOL) value {
+  result.hasIsCacheable = YES;
+  result.isCacheable = value;
+  return self;
+}
+- (VideoFrameV2Builder*) clearIsCacheable {
+  result.hasIsCacheable = NO;
+  result.isCacheable = NO;
+  return self;
+}
+- (BOOL) hasIsLastChunkFrame {
+  return result.hasIsLastChunkFrame;
+}
+- (BOOL) isLastChunkFrame {
+  return result.isLastChunkFrame;
+}
+- (VideoFrameV2Builder*) setIsLastChunkFrame:(BOOL) value {
+  result.hasIsLastChunkFrame = YES;
+  result.isLastChunkFrame = value;
+  return self;
+}
+- (VideoFrameV2Builder*) clearIsLastChunkFrame {
+  result.hasIsLastChunkFrame = NO;
+  result.isLastChunkFrame = NO;
+  return self;
+}
+@end
+
+@interface VideoFrameV3 ()
+@property (strong) NSMutableArray * nalsArray;
+@property Float64 timestamp;
+@property (strong) NSString* cacheToken;
+@property Float64 chunkStartTime;
+@end
+
+@implementation VideoFrameV3
+
+@synthesize nalsArray;
+@dynamic nals;
+- (BOOL) hasTimestamp {
+  return !!hasTimestamp_;
+}
+- (void) setHasTimestamp:(BOOL) value_ {
+  hasTimestamp_ = !!value_;
+}
+@synthesize timestamp;
+- (BOOL) hasCacheToken {
+  return !!hasCacheToken_;
+}
+- (void) setHasCacheToken:(BOOL) value_ {
+  hasCacheToken_ = !!value_;
+}
+@synthesize cacheToken;
+- (BOOL) hasChunkStartTime {
+  return !!hasChunkStartTime_;
+}
+- (void) setHasChunkStartTime:(BOOL) value_ {
+  hasChunkStartTime_ = !!value_;
+}
+@synthesize chunkStartTime;
+- (id) init {
+  if ((self = [super init])) {
+    self.timestamp = 0;
+    self.cacheToken = @"";
+    self.chunkStartTime = 0;
+  }
+  return self;
+}
+static VideoFrameV3* defaultVideoFrameV3Instance = nil;
++ (void) initialize {
+  if (self == [VideoFrameV3 class]) {
+    defaultVideoFrameV3Instance = [[VideoFrameV3 alloc] init];
+  }
+}
++ (VideoFrameV3*) defaultInstance {
+  return defaultVideoFrameV3Instance;
+}
+- (VideoFrameV3*) defaultInstance {
+  return defaultVideoFrameV3Instance;
+}
+- (NSArray *)nals {
+  return nalsArray;
+}
+- (NSData*)nalsAtIndex:(NSUInteger)index {
+  return [nalsArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  [self.nalsArray enumerateObjectsUsingBlock:^(NSData *element, NSUInteger idx, BOOL *stop) {
+    [output writeData:1 value:element];
+  }];
+  if (self.hasTimestamp) {
+    [output writeDouble:2 value:self.timestamp];
+  }
+  if (self.hasCacheToken) {
+    [output writeString:3 value:self.cacheToken];
+  }
+  if (self.hasChunkStartTime) {
+    [output writeDouble:4 value:self.chunkStartTime];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.nalsArray.count;
+    [self.nalsArray enumerateObjectsUsingBlock:^(NSData *element, NSUInteger idx, BOOL *stop) {
+      dataSize += computeDataSizeNoTag(element);
+    }];
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  if (self.hasTimestamp) {
+    size_ += computeDoubleSize(2, self.timestamp);
+  }
+  if (self.hasCacheToken) {
+    size_ += computeStringSize(3, self.cacheToken);
+  }
+  if (self.hasChunkStartTime) {
+    size_ += computeDoubleSize(4, self.chunkStartTime);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (VideoFrameV3*) parseFromData:(NSData*) data {
+  return (VideoFrameV3*)[[[VideoFrameV3 builder] mergeFromData:data] build];
+}
++ (VideoFrameV3*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (VideoFrameV3*)[[[VideoFrameV3 builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (VideoFrameV3*) parseFromInputStream:(NSInputStream*) input {
+  return (VideoFrameV3*)[[[VideoFrameV3 builder] mergeFromInputStream:input] build];
+}
++ (VideoFrameV3*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (VideoFrameV3*)[[[VideoFrameV3 builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (VideoFrameV3*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (VideoFrameV3*)[[[VideoFrameV3 builder] mergeFromCodedInputStream:input] build];
+}
++ (VideoFrameV3*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (VideoFrameV3*)[[[VideoFrameV3 builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (VideoFrameV3Builder*) builder {
+  return [[VideoFrameV3Builder alloc] init];
+}
++ (VideoFrameV3Builder*) builderWithPrototype:(VideoFrameV3*) prototype {
+  return [[VideoFrameV3 builder] mergeFrom:prototype];
+}
+- (VideoFrameV3Builder*) builder {
+  return [VideoFrameV3 builder];
+}
+- (VideoFrameV3Builder*) toBuilder {
+  return [VideoFrameV3 builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.nalsArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"nals", obj];
+  }];
+  if (self.hasTimestamp) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"timestamp", [NSNumber numberWithDouble:self.timestamp]];
+  }
+  if (self.hasCacheToken) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"cacheToken", self.cacheToken];
+  }
+  if (self.hasChunkStartTime) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"chunkStartTime", [NSNumber numberWithDouble:self.chunkStartTime]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[VideoFrameV3 class]]) {
+    return NO;
+  }
+  VideoFrameV3 *otherMessage = other;
+  return
+      [self.nalsArray isEqualToArray:otherMessage.nalsArray] &&
+      self.hasTimestamp == otherMessage.hasTimestamp &&
+      (!self.hasTimestamp || self.timestamp == otherMessage.timestamp) &&
+      self.hasCacheToken == otherMessage.hasCacheToken &&
+      (!self.hasCacheToken || [self.cacheToken isEqual:otherMessage.cacheToken]) &&
+      self.hasChunkStartTime == otherMessage.hasChunkStartTime &&
+      (!self.hasChunkStartTime || self.chunkStartTime == otherMessage.chunkStartTime) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  [self.nalsArray enumerateObjectsUsingBlock:^(id element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasTimestamp) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithDouble:self.timestamp] hash];
+  }
+  if (self.hasCacheToken) {
+    hashCode = hashCode * 31 + [self.cacheToken hash];
+  }
+  if (self.hasChunkStartTime) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithDouble:self.chunkStartTime] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface VideoFrameV3Builder()
+@property (strong) VideoFrameV3* result;
+@end
+
+@implementation VideoFrameV3Builder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[VideoFrameV3 alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (VideoFrameV3Builder*) clear {
+  self.result = [[VideoFrameV3 alloc] init];
+  return self;
+}
+- (VideoFrameV3Builder*) clone {
+  return [VideoFrameV3 builderWithPrototype:result];
+}
+- (VideoFrameV3*) defaultInstance {
+  return [VideoFrameV3 defaultInstance];
+}
+- (VideoFrameV3*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (VideoFrameV3*) buildPartial {
+  VideoFrameV3* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (VideoFrameV3Builder*) mergeFrom:(VideoFrameV3*) other {
+  if (other == [VideoFrameV3 defaultInstance]) {
+    return self;
+  }
+  if (other.nalsArray.count > 0) {
+    if (result.nalsArray == nil) {
+      result.nalsArray = [[NSMutableArray alloc] initWithArray:other.nalsArray];
+    } else {
+      [result.nalsArray addObjectsFromArray:other.nalsArray];
+    }
+  }
+  if (other.hasTimestamp) {
+    [self setTimestamp:other.timestamp];
+  }
+  if (other.hasCacheToken) {
+    [self setCacheToken:other.cacheToken];
+  }
+  if (other.hasChunkStartTime) {
+    [self setChunkStartTime:other.chunkStartTime];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (VideoFrameV3Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (VideoFrameV3Builder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self addNals:[input readData]];
+        break;
+      }
+      case 17: {
+        [self setTimestamp:[input readDouble]];
+        break;
+      }
+      case 26: {
+        [self setCacheToken:[input readString]];
+        break;
+      }
+      case 33: {
+        [self setChunkStartTime:[input readDouble]];
+        break;
+      }
+    }
+  }
+}
+- (NSMutableArray *)nals {
+  return result.nalsArray;
+}
+- (NSData*)nalsAtIndex:(NSUInteger)index {
+  return [result nalsAtIndex:index];
+}
+- (VideoFrameV3Builder *)addNals:(NSData*)value {
+  if (result.nalsArray == nil) {
+    result.nalsArray = [[NSMutableArray alloc]init];
+  }
+  [result.nalsArray addObject:value];
+  return self;
+}
+- (VideoFrameV3Builder *)setNalsArray:(NSArray *)array {
+  result.nalsArray = [[NSMutableArray alloc] initWithArray:array];
+  return self;
+}
+- (VideoFrameV3Builder *)clearNals {
+  result.nalsArray = nil;
+  return self;
+}
+- (BOOL) hasTimestamp {
+  return result.hasTimestamp;
+}
+- (Float64) timestamp {
+  return result.timestamp;
+}
+- (VideoFrameV3Builder*) setTimestamp:(Float64) value {
+  result.hasTimestamp = YES;
+  result.timestamp = value;
+  return self;
+}
+- (VideoFrameV3Builder*) clearTimestamp {
+  result.hasTimestamp = NO;
+  result.timestamp = 0;
+  return self;
+}
+- (BOOL) hasCacheToken {
+  return result.hasCacheToken;
+}
+- (NSString*) cacheToken {
+  return result.cacheToken;
+}
+- (VideoFrameV3Builder*) setCacheToken:(NSString*) value {
+  result.hasCacheToken = YES;
+  result.cacheToken = value;
+  return self;
+}
+- (VideoFrameV3Builder*) clearCacheToken {
+  result.hasCacheToken = NO;
+  result.cacheToken = @"";
+  return self;
+}
+- (BOOL) hasChunkStartTime {
+  return result.hasChunkStartTime;
+}
+- (Float64) chunkStartTime {
+  return result.chunkStartTime;
+}
+- (VideoFrameV3Builder*) setChunkStartTime:(Float64) value {
+  result.hasChunkStartTime = YES;
+  result.chunkStartTime = value;
+  return self;
+}
+- (VideoFrameV3Builder*) clearChunkStartTime {
+  result.hasChunkStartTime = NO;
+  result.chunkStartTime = 0;
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Setuptalk.pb.h b/src/gen_proto/Setuptalk.pb.h
new file mode 100644
index 0000000..2e58c5c
--- /dev/null
+++ b/src/gen_proto/Setuptalk.pb.h
@@ -0,0 +1,674 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class ST_DeviceInfo;
+@class ST_DeviceInfoBuilder;
+@class ST_InitSetup;
+@class ST_InitSetupBuilder;
+@class ST_JpakeBegin;
+@class ST_JpakeBeginBuilder;
+@class ST_JpakeResponse;
+@class ST_JpakeResponseBuilder;
+@class ST_JpakeStep;
+@class ST_JpakeStepBuilder;
+@class ST_WifiConnect;
+@class ST_WifiConnectBuilder;
+@class ST_WifiConnectStatus;
+@class ST_WifiConnectStatusBuilder;
+@class ST_WifiScan;
+@class ST_WifiScanBuilder;
+@class ST_WifiScanList;
+@class ST_WifiScanListBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  ST_PacketTypePacketTypeInitSetup = 1,
+  ST_PacketTypePacketTypeWifiScan = 2,
+  ST_PacketTypePacketTypeWifiConnect = 3,
+  ST_PacketTypePacketTypeJpakeBegin = 32,
+  ST_PacketTypePacketTypeJpakeResponse = 48,
+  ST_PacketTypePacketTypeDeviceInfo = 64,
+  ST_PacketTypePacketTypeWifiScanList = 65,
+  ST_PacketTypePacketTypeWifiConnectStatus = 66,
+} ST_PacketType;
+
+BOOL ST_PacketTypeIsValidValue(ST_PacketType value);
+
+typedef enum {
+  ST_WifiConnectNetworkSecurityTypeNone = 0,
+  ST_WifiConnectNetworkSecurityTypeWep = 1,
+  ST_WifiConnectNetworkSecurityTypeWpaPersonal = 2,
+} ST_WifiConnectNetworkSecurityType;
+
+BOOL ST_WifiConnectNetworkSecurityTypeIsValidValue(ST_WifiConnectNetworkSecurityType value);
+
+typedef enum {
+  ST_WifiConnectStatusResultSuccess = 0,
+  ST_WifiConnectStatusResultBadPassword = 1,
+  ST_WifiConnectStatusResultNetworkNotFound = 2,
+  ST_WifiConnectStatusResultNoDhcp = 3,
+  ST_WifiConnectStatusResultNoInternet = 4,
+  ST_WifiConnectStatusResultNoAuth = 5,
+} ST_WifiConnectStatusResult;
+
+BOOL ST_WifiConnectStatusResultIsValidValue(ST_WifiConnectStatusResult value);
+
+
+@interface SetuptalkRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface ST_JpakeStep : PBGeneratedMessage {
+@private
+  BOOL hasGx_:1;
+  BOOL hasGr_:1;
+  BOOL hasB_:1;
+  NSData* gx;
+  NSData* gr;
+  NSData* b;
+}
+- (BOOL) hasGx;
+- (BOOL) hasGr;
+- (BOOL) hasB;
+@property (readonly, strong) NSData* gx;
+@property (readonly, strong) NSData* gr;
+@property (readonly, strong) NSData* b;
+
++ (ST_JpakeStep*) defaultInstance;
+- (ST_JpakeStep*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_JpakeStepBuilder*) builder;
++ (ST_JpakeStepBuilder*) builder;
++ (ST_JpakeStepBuilder*) builderWithPrototype:(ST_JpakeStep*) prototype;
+- (ST_JpakeStepBuilder*) toBuilder;
+
++ (ST_JpakeStep*) parseFromData:(NSData*) data;
++ (ST_JpakeStep*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_JpakeStep*) parseFromInputStream:(NSInputStream*) input;
++ (ST_JpakeStep*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_JpakeStep*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_JpakeStep*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_JpakeStepBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_JpakeStep* result;
+}
+
+- (ST_JpakeStep*) defaultInstance;
+
+- (ST_JpakeStepBuilder*) clear;
+- (ST_JpakeStepBuilder*) clone;
+
+- (ST_JpakeStep*) build;
+- (ST_JpakeStep*) buildPartial;
+
+- (ST_JpakeStepBuilder*) mergeFrom:(ST_JpakeStep*) other;
+- (ST_JpakeStepBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_JpakeStepBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasGx;
+- (NSData*) gx;
+- (ST_JpakeStepBuilder*) setGx:(NSData*) value;
+- (ST_JpakeStepBuilder*) clearGx;
+
+- (BOOL) hasGr;
+- (NSData*) gr;
+- (ST_JpakeStepBuilder*) setGr:(NSData*) value;
+- (ST_JpakeStepBuilder*) clearGr;
+
+- (BOOL) hasB;
+- (NSData*) b;
+- (ST_JpakeStepBuilder*) setB:(NSData*) value;
+- (ST_JpakeStepBuilder*) clearB;
+@end
+
+@interface ST_JpakeBegin : PBGeneratedMessage {
+@private
+  BOOL hasAstep1P1_:1;
+  BOOL hasAstep1P2_:1;
+  ST_JpakeStep* astep1P1;
+  ST_JpakeStep* astep1P2;
+}
+- (BOOL) hasAstep1P1;
+- (BOOL) hasAstep1P2;
+@property (readonly, strong) ST_JpakeStep* astep1P1;
+@property (readonly, strong) ST_JpakeStep* astep1P2;
+
++ (ST_JpakeBegin*) defaultInstance;
+- (ST_JpakeBegin*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_JpakeBeginBuilder*) builder;
++ (ST_JpakeBeginBuilder*) builder;
++ (ST_JpakeBeginBuilder*) builderWithPrototype:(ST_JpakeBegin*) prototype;
+- (ST_JpakeBeginBuilder*) toBuilder;
+
++ (ST_JpakeBegin*) parseFromData:(NSData*) data;
++ (ST_JpakeBegin*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_JpakeBegin*) parseFromInputStream:(NSInputStream*) input;
++ (ST_JpakeBegin*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_JpakeBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_JpakeBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_JpakeBeginBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_JpakeBegin* result;
+}
+
+- (ST_JpakeBegin*) defaultInstance;
+
+- (ST_JpakeBeginBuilder*) clear;
+- (ST_JpakeBeginBuilder*) clone;
+
+- (ST_JpakeBegin*) build;
+- (ST_JpakeBegin*) buildPartial;
+
+- (ST_JpakeBeginBuilder*) mergeFrom:(ST_JpakeBegin*) other;
+- (ST_JpakeBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_JpakeBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasAstep1P1;
+- (ST_JpakeStep*) astep1P1;
+- (ST_JpakeBeginBuilder*) setAstep1P1:(ST_JpakeStep*) value;
+- (ST_JpakeBeginBuilder*) setAstep1P1Builder:(ST_JpakeStepBuilder*) builderForValue;
+- (ST_JpakeBeginBuilder*) mergeAstep1P1:(ST_JpakeStep*) value;
+- (ST_JpakeBeginBuilder*) clearAstep1P1;
+
+- (BOOL) hasAstep1P2;
+- (ST_JpakeStep*) astep1P2;
+- (ST_JpakeBeginBuilder*) setAstep1P2:(ST_JpakeStep*) value;
+- (ST_JpakeBeginBuilder*) setAstep1P2Builder:(ST_JpakeStepBuilder*) builderForValue;
+- (ST_JpakeBeginBuilder*) mergeAstep1P2:(ST_JpakeStep*) value;
+- (ST_JpakeBeginBuilder*) clearAstep1P2;
+@end
+
+@interface ST_JpakeResponse : PBGeneratedMessage {
+@private
+  BOOL hasCstep1P1_:1;
+  BOOL hasCstep1P2_:1;
+  BOOL hasCstep2_:1;
+  ST_JpakeStep* cstep1P1;
+  ST_JpakeStep* cstep1P2;
+  ST_JpakeStep* cstep2;
+}
+- (BOOL) hasCstep1P1;
+- (BOOL) hasCstep1P2;
+- (BOOL) hasCstep2;
+@property (readonly, strong) ST_JpakeStep* cstep1P1;
+@property (readonly, strong) ST_JpakeStep* cstep1P2;
+@property (readonly, strong) ST_JpakeStep* cstep2;
+
++ (ST_JpakeResponse*) defaultInstance;
+- (ST_JpakeResponse*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_JpakeResponseBuilder*) builder;
++ (ST_JpakeResponseBuilder*) builder;
++ (ST_JpakeResponseBuilder*) builderWithPrototype:(ST_JpakeResponse*) prototype;
+- (ST_JpakeResponseBuilder*) toBuilder;
+
++ (ST_JpakeResponse*) parseFromData:(NSData*) data;
++ (ST_JpakeResponse*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_JpakeResponse*) parseFromInputStream:(NSInputStream*) input;
++ (ST_JpakeResponse*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_JpakeResponse*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_JpakeResponse*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_JpakeResponseBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_JpakeResponse* result;
+}
+
+- (ST_JpakeResponse*) defaultInstance;
+
+- (ST_JpakeResponseBuilder*) clear;
+- (ST_JpakeResponseBuilder*) clone;
+
+- (ST_JpakeResponse*) build;
+- (ST_JpakeResponse*) buildPartial;
+
+- (ST_JpakeResponseBuilder*) mergeFrom:(ST_JpakeResponse*) other;
+- (ST_JpakeResponseBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_JpakeResponseBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasCstep1P1;
+- (ST_JpakeStep*) cstep1P1;
+- (ST_JpakeResponseBuilder*) setCstep1P1:(ST_JpakeStep*) value;
+- (ST_JpakeResponseBuilder*) setCstep1P1Builder:(ST_JpakeStepBuilder*) builderForValue;
+- (ST_JpakeResponseBuilder*) mergeCstep1P1:(ST_JpakeStep*) value;
+- (ST_JpakeResponseBuilder*) clearCstep1P1;
+
+- (BOOL) hasCstep1P2;
+- (ST_JpakeStep*) cstep1P2;
+- (ST_JpakeResponseBuilder*) setCstep1P2:(ST_JpakeStep*) value;
+- (ST_JpakeResponseBuilder*) setCstep1P2Builder:(ST_JpakeStepBuilder*) builderForValue;
+- (ST_JpakeResponseBuilder*) mergeCstep1P2:(ST_JpakeStep*) value;
+- (ST_JpakeResponseBuilder*) clearCstep1P2;
+
+- (BOOL) hasCstep2;
+- (ST_JpakeStep*) cstep2;
+- (ST_JpakeResponseBuilder*) setCstep2:(ST_JpakeStep*) value;
+- (ST_JpakeResponseBuilder*) setCstep2Builder:(ST_JpakeStepBuilder*) builderForValue;
+- (ST_JpakeResponseBuilder*) mergeCstep2:(ST_JpakeStep*) value;
+- (ST_JpakeResponseBuilder*) clearCstep2;
+@end
+
+@interface ST_InitSetup : PBGeneratedMessage {
+@private
+  BOOL hasAstep2_:1;
+  BOOL hasStep3A_:1;
+  ST_JpakeStep* astep2;
+  NSData* step3A;
+}
+- (BOOL) hasAstep2;
+- (BOOL) hasStep3A;
+@property (readonly, strong) ST_JpakeStep* astep2;
+@property (readonly, strong) NSData* step3A;
+
++ (ST_InitSetup*) defaultInstance;
+- (ST_InitSetup*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_InitSetupBuilder*) builder;
++ (ST_InitSetupBuilder*) builder;
++ (ST_InitSetupBuilder*) builderWithPrototype:(ST_InitSetup*) prototype;
+- (ST_InitSetupBuilder*) toBuilder;
+
++ (ST_InitSetup*) parseFromData:(NSData*) data;
++ (ST_InitSetup*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_InitSetup*) parseFromInputStream:(NSInputStream*) input;
++ (ST_InitSetup*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_InitSetup*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_InitSetup*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_InitSetupBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_InitSetup* result;
+}
+
+- (ST_InitSetup*) defaultInstance;
+
+- (ST_InitSetupBuilder*) clear;
+- (ST_InitSetupBuilder*) clone;
+
+- (ST_InitSetup*) build;
+- (ST_InitSetup*) buildPartial;
+
+- (ST_InitSetupBuilder*) mergeFrom:(ST_InitSetup*) other;
+- (ST_InitSetupBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_InitSetupBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasAstep2;
+- (ST_JpakeStep*) astep2;
+- (ST_InitSetupBuilder*) setAstep2:(ST_JpakeStep*) value;
+- (ST_InitSetupBuilder*) setAstep2Builder:(ST_JpakeStepBuilder*) builderForValue;
+- (ST_InitSetupBuilder*) mergeAstep2:(ST_JpakeStep*) value;
+- (ST_InitSetupBuilder*) clearAstep2;
+
+- (BOOL) hasStep3A;
+- (NSData*) step3A;
+- (ST_InitSetupBuilder*) setStep3A:(NSData*) value;
+- (ST_InitSetupBuilder*) clearStep3A;
+@end
+
+@interface ST_DeviceInfo : PBGeneratedMessage {
+@private
+  BOOL hasNonce_:1;
+  BOOL hasToken_:1;
+  BOOL hasFlags_:1;
+  BOOL hasStep3B_:1;
+  NSData* nonce;
+  NSData* token;
+  NSData* flags;
+  NSData* step3B;
+}
+- (BOOL) hasNonce;
+- (BOOL) hasToken;
+- (BOOL) hasFlags;
+- (BOOL) hasStep3B;
+@property (readonly, strong) NSData* nonce;
+@property (readonly, strong) NSData* token;
+@property (readonly, strong) NSData* flags;
+@property (readonly, strong) NSData* step3B;
+
++ (ST_DeviceInfo*) defaultInstance;
+- (ST_DeviceInfo*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_DeviceInfoBuilder*) builder;
++ (ST_DeviceInfoBuilder*) builder;
++ (ST_DeviceInfoBuilder*) builderWithPrototype:(ST_DeviceInfo*) prototype;
+- (ST_DeviceInfoBuilder*) toBuilder;
+
++ (ST_DeviceInfo*) parseFromData:(NSData*) data;
++ (ST_DeviceInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_DeviceInfo*) parseFromInputStream:(NSInputStream*) input;
++ (ST_DeviceInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_DeviceInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_DeviceInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_DeviceInfoBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_DeviceInfo* result;
+}
+
+- (ST_DeviceInfo*) defaultInstance;
+
+- (ST_DeviceInfoBuilder*) clear;
+- (ST_DeviceInfoBuilder*) clone;
+
+- (ST_DeviceInfo*) build;
+- (ST_DeviceInfo*) buildPartial;
+
+- (ST_DeviceInfoBuilder*) mergeFrom:(ST_DeviceInfo*) other;
+- (ST_DeviceInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_DeviceInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasNonce;
+- (NSData*) nonce;
+- (ST_DeviceInfoBuilder*) setNonce:(NSData*) value;
+- (ST_DeviceInfoBuilder*) clearNonce;
+
+- (BOOL) hasToken;
+- (NSData*) token;
+- (ST_DeviceInfoBuilder*) setToken:(NSData*) value;
+- (ST_DeviceInfoBuilder*) clearToken;
+
+- (BOOL) hasFlags;
+- (NSData*) flags;
+- (ST_DeviceInfoBuilder*) setFlags:(NSData*) value;
+- (ST_DeviceInfoBuilder*) clearFlags;
+
+- (BOOL) hasStep3B;
+- (NSData*) step3B;
+- (ST_DeviceInfoBuilder*) setStep3B:(NSData*) value;
+- (ST_DeviceInfoBuilder*) clearStep3B;
+@end
+
+@interface ST_WifiScan : PBGeneratedMessage {
+@private
+  BOOL hasAuthTag_:1;
+  NSData* authTag;
+}
+- (BOOL) hasAuthTag;
+@property (readonly, strong) NSData* authTag;
+
++ (ST_WifiScan*) defaultInstance;
+- (ST_WifiScan*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_WifiScanBuilder*) builder;
++ (ST_WifiScanBuilder*) builder;
++ (ST_WifiScanBuilder*) builderWithPrototype:(ST_WifiScan*) prototype;
+- (ST_WifiScanBuilder*) toBuilder;
+
++ (ST_WifiScan*) parseFromData:(NSData*) data;
++ (ST_WifiScan*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiScan*) parseFromInputStream:(NSInputStream*) input;
++ (ST_WifiScan*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiScan*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_WifiScan*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_WifiScanBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_WifiScan* result;
+}
+
+- (ST_WifiScan*) defaultInstance;
+
+- (ST_WifiScanBuilder*) clear;
+- (ST_WifiScanBuilder*) clone;
+
+- (ST_WifiScan*) build;
+- (ST_WifiScan*) buildPartial;
+
+- (ST_WifiScanBuilder*) mergeFrom:(ST_WifiScan*) other;
+- (ST_WifiScanBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_WifiScanBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasAuthTag;
+- (NSData*) authTag;
+- (ST_WifiScanBuilder*) setAuthTag:(NSData*) value;
+- (ST_WifiScanBuilder*) clearAuthTag;
+@end
+
+@interface ST_WifiConnect : PBGeneratedMessage {
+@private
+  BOOL hasIsManual_:1;
+  BOOL hasBssid_:1;
+  BOOL hasSsid_:1;
+  BOOL hasEncryptedPassword_:1;
+  BOOL hasAuthTag_:1;
+  BOOL hasJpakeHmac_:1;
+  BOOL hasType_:1;
+  BOOL isManual_:1;
+  NSString* bssid;
+  NSString* ssid;
+  NSData* encryptedPassword;
+  NSData* authTag;
+  NSData* jpakeHmac;
+  ST_WifiConnectNetworkSecurityType type;
+}
+- (BOOL) hasBssid;
+- (BOOL) hasSsid;
+- (BOOL) hasEncryptedPassword;
+- (BOOL) hasType;
+- (BOOL) hasIsManual;
+- (BOOL) hasAuthTag;
+- (BOOL) hasJpakeHmac;
+@property (readonly, strong) NSString* bssid;
+@property (readonly, strong) NSString* ssid;
+@property (readonly, strong) NSData* encryptedPassword;
+@property (readonly) ST_WifiConnectNetworkSecurityType type;
+- (BOOL) isManual;
+@property (readonly, strong) NSData* authTag;
+@property (readonly, strong) NSData* jpakeHmac;
+
++ (ST_WifiConnect*) defaultInstance;
+- (ST_WifiConnect*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_WifiConnectBuilder*) builder;
++ (ST_WifiConnectBuilder*) builder;
++ (ST_WifiConnectBuilder*) builderWithPrototype:(ST_WifiConnect*) prototype;
+- (ST_WifiConnectBuilder*) toBuilder;
+
++ (ST_WifiConnect*) parseFromData:(NSData*) data;
++ (ST_WifiConnect*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiConnect*) parseFromInputStream:(NSInputStream*) input;
++ (ST_WifiConnect*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiConnect*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_WifiConnect*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_WifiConnectBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_WifiConnect* result;
+}
+
+- (ST_WifiConnect*) defaultInstance;
+
+- (ST_WifiConnectBuilder*) clear;
+- (ST_WifiConnectBuilder*) clone;
+
+- (ST_WifiConnect*) build;
+- (ST_WifiConnect*) buildPartial;
+
+- (ST_WifiConnectBuilder*) mergeFrom:(ST_WifiConnect*) other;
+- (ST_WifiConnectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_WifiConnectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasBssid;
+- (NSString*) bssid;
+- (ST_WifiConnectBuilder*) setBssid:(NSString*) value;
+- (ST_WifiConnectBuilder*) clearBssid;
+
+- (BOOL) hasSsid;
+- (NSString*) ssid;
+- (ST_WifiConnectBuilder*) setSsid:(NSString*) value;
+- (ST_WifiConnectBuilder*) clearSsid;
+
+- (BOOL) hasEncryptedPassword;
+- (NSData*) encryptedPassword;
+- (ST_WifiConnectBuilder*) setEncryptedPassword:(NSData*) value;
+- (ST_WifiConnectBuilder*) clearEncryptedPassword;
+
+- (BOOL) hasType;
+- (ST_WifiConnectNetworkSecurityType) type;
+- (ST_WifiConnectBuilder*) setType:(ST_WifiConnectNetworkSecurityType) value;
+- (ST_WifiConnectBuilder*) clearType;
+
+- (BOOL) hasIsManual;
+- (BOOL) isManual;
+- (ST_WifiConnectBuilder*) setIsManual:(BOOL) value;
+- (ST_WifiConnectBuilder*) clearIsManual;
+
+- (BOOL) hasAuthTag;
+- (NSData*) authTag;
+- (ST_WifiConnectBuilder*) setAuthTag:(NSData*) value;
+- (ST_WifiConnectBuilder*) clearAuthTag;
+
+- (BOOL) hasJpakeHmac;
+- (NSData*) jpakeHmac;
+- (ST_WifiConnectBuilder*) setJpakeHmac:(NSData*) value;
+- (ST_WifiConnectBuilder*) clearJpakeHmac;
+@end
+
+@interface ST_WifiScanList : PBGeneratedMessage {
+@private
+  BOOL hasList_:1;
+  NSString* list;
+}
+- (BOOL) hasList;
+@property (readonly, strong) NSString* list;
+
++ (ST_WifiScanList*) defaultInstance;
+- (ST_WifiScanList*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_WifiScanListBuilder*) builder;
++ (ST_WifiScanListBuilder*) builder;
++ (ST_WifiScanListBuilder*) builderWithPrototype:(ST_WifiScanList*) prototype;
+- (ST_WifiScanListBuilder*) toBuilder;
+
++ (ST_WifiScanList*) parseFromData:(NSData*) data;
++ (ST_WifiScanList*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiScanList*) parseFromInputStream:(NSInputStream*) input;
++ (ST_WifiScanList*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiScanList*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_WifiScanList*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_WifiScanListBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_WifiScanList* result;
+}
+
+- (ST_WifiScanList*) defaultInstance;
+
+- (ST_WifiScanListBuilder*) clear;
+- (ST_WifiScanListBuilder*) clone;
+
+- (ST_WifiScanList*) build;
+- (ST_WifiScanList*) buildPartial;
+
+- (ST_WifiScanListBuilder*) mergeFrom:(ST_WifiScanList*) other;
+- (ST_WifiScanListBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_WifiScanListBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasList;
+- (NSString*) list;
+- (ST_WifiScanListBuilder*) setList:(NSString*) value;
+- (ST_WifiScanListBuilder*) clearList;
+@end
+
+@interface ST_WifiConnectStatus : PBGeneratedMessage {
+@private
+  BOOL hasDebugLog_:1;
+  BOOL hasConnectResult_:1;
+  NSString* debugLog;
+  ST_WifiConnectStatusResult connectResult;
+}
+- (BOOL) hasConnectResult;
+- (BOOL) hasDebugLog;
+@property (readonly) ST_WifiConnectStatusResult connectResult;
+@property (readonly, strong) NSString* debugLog;
+
++ (ST_WifiConnectStatus*) defaultInstance;
+- (ST_WifiConnectStatus*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (ST_WifiConnectStatusBuilder*) builder;
++ (ST_WifiConnectStatusBuilder*) builder;
++ (ST_WifiConnectStatusBuilder*) builderWithPrototype:(ST_WifiConnectStatus*) prototype;
+- (ST_WifiConnectStatusBuilder*) toBuilder;
+
++ (ST_WifiConnectStatus*) parseFromData:(NSData*) data;
++ (ST_WifiConnectStatus*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiConnectStatus*) parseFromInputStream:(NSInputStream*) input;
++ (ST_WifiConnectStatus*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (ST_WifiConnectStatus*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (ST_WifiConnectStatus*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface ST_WifiConnectStatusBuilder : PBGeneratedMessageBuilder {
+@private
+  ST_WifiConnectStatus* result;
+}
+
+- (ST_WifiConnectStatus*) defaultInstance;
+
+- (ST_WifiConnectStatusBuilder*) clear;
+- (ST_WifiConnectStatusBuilder*) clone;
+
+- (ST_WifiConnectStatus*) build;
+- (ST_WifiConnectStatus*) buildPartial;
+
+- (ST_WifiConnectStatusBuilder*) mergeFrom:(ST_WifiConnectStatus*) other;
+- (ST_WifiConnectStatusBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (ST_WifiConnectStatusBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasConnectResult;
+- (ST_WifiConnectStatusResult) connectResult;
+- (ST_WifiConnectStatusBuilder*) setConnectResult:(ST_WifiConnectStatusResult) value;
+- (ST_WifiConnectStatusBuilder*) clearConnectResult;
+
+- (BOOL) hasDebugLog;
+- (NSString*) debugLog;
+- (ST_WifiConnectStatusBuilder*) setDebugLog:(NSString*) value;
+- (ST_WifiConnectStatusBuilder*) clearDebugLog;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Setuptalk.pb.m b/src/gen_proto/Setuptalk.pb.m
new file mode 100644
index 0000000..358de97
--- /dev/null
+++ b/src/gen_proto/Setuptalk.pb.m
@@ -0,0 +1,2751 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Setuptalk.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation SetuptalkRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [SetuptalkRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+BOOL ST_PacketTypeIsValidValue(ST_PacketType value) {
+  switch (value) {
+    case ST_PacketTypePacketTypeInitSetup:
+    case ST_PacketTypePacketTypeWifiScan:
+    case ST_PacketTypePacketTypeWifiConnect:
+    case ST_PacketTypePacketTypeJpakeBegin:
+    case ST_PacketTypePacketTypeJpakeResponse:
+    case ST_PacketTypePacketTypeDeviceInfo:
+    case ST_PacketTypePacketTypeWifiScanList:
+    case ST_PacketTypePacketTypeWifiConnectStatus:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface ST_JpakeStep ()
+@property (strong) NSData* gx;
+@property (strong) NSData* gr;
+@property (strong) NSData* b;
+@end
+
+@implementation ST_JpakeStep
+
+- (BOOL) hasGx {
+  return !!hasGx_;
+}
+- (void) setHasGx:(BOOL) value_ {
+  hasGx_ = !!value_;
+}
+@synthesize gx;
+- (BOOL) hasGr {
+  return !!hasGr_;
+}
+- (void) setHasGr:(BOOL) value_ {
+  hasGr_ = !!value_;
+}
+@synthesize gr;
+- (BOOL) hasB {
+  return !!hasB_;
+}
+- (void) setHasB:(BOOL) value_ {
+  hasB_ = !!value_;
+}
+@synthesize b;
+- (id) init {
+  if ((self = [super init])) {
+    self.gx = [NSData data];
+    self.gr = [NSData data];
+    self.b = [NSData data];
+  }
+  return self;
+}
+static ST_JpakeStep* defaultST_JpakeStepInstance = nil;
++ (void) initialize {
+  if (self == [ST_JpakeStep class]) {
+    defaultST_JpakeStepInstance = [[ST_JpakeStep alloc] init];
+  }
+}
++ (ST_JpakeStep*) defaultInstance {
+  return defaultST_JpakeStepInstance;
+}
+- (ST_JpakeStep*) defaultInstance {
+  return defaultST_JpakeStepInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasGx) {
+    [output writeData:1 value:self.gx];
+  }
+  if (self.hasGr) {
+    [output writeData:2 value:self.gr];
+  }
+  if (self.hasB) {
+    [output writeData:3 value:self.b];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasGx) {
+    size_ += computeDataSize(1, self.gx);
+  }
+  if (self.hasGr) {
+    size_ += computeDataSize(2, self.gr);
+  }
+  if (self.hasB) {
+    size_ += computeDataSize(3, self.b);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_JpakeStep*) parseFromData:(NSData*) data {
+  return (ST_JpakeStep*)[[[ST_JpakeStep builder] mergeFromData:data] build];
+}
++ (ST_JpakeStep*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeStep*)[[[ST_JpakeStep builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeStep*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_JpakeStep*)[[[ST_JpakeStep builder] mergeFromInputStream:input] build];
+}
++ (ST_JpakeStep*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeStep*)[[[ST_JpakeStep builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeStep*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_JpakeStep*)[[[ST_JpakeStep builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_JpakeStep*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeStep*)[[[ST_JpakeStep builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeStepBuilder*) builder {
+  return [[ST_JpakeStepBuilder alloc] init];
+}
++ (ST_JpakeStepBuilder*) builderWithPrototype:(ST_JpakeStep*) prototype {
+  return [[ST_JpakeStep builder] mergeFrom:prototype];
+}
+- (ST_JpakeStepBuilder*) builder {
+  return [ST_JpakeStep builder];
+}
+- (ST_JpakeStepBuilder*) toBuilder {
+  return [ST_JpakeStep builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasGx) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"gx", self.gx];
+  }
+  if (self.hasGr) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"gr", self.gr];
+  }
+  if (self.hasB) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"b", self.b];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_JpakeStep class]]) {
+    return NO;
+  }
+  ST_JpakeStep *otherMessage = other;
+  return
+      self.hasGx == otherMessage.hasGx &&
+      (!self.hasGx || [self.gx isEqual:otherMessage.gx]) &&
+      self.hasGr == otherMessage.hasGr &&
+      (!self.hasGr || [self.gr isEqual:otherMessage.gr]) &&
+      self.hasB == otherMessage.hasB &&
+      (!self.hasB || [self.b isEqual:otherMessage.b]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasGx) {
+    hashCode = hashCode * 31 + [self.gx hash];
+  }
+  if (self.hasGr) {
+    hashCode = hashCode * 31 + [self.gr hash];
+  }
+  if (self.hasB) {
+    hashCode = hashCode * 31 + [self.b hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ST_JpakeStepBuilder()
+@property (strong) ST_JpakeStep* result;
+@end
+
+@implementation ST_JpakeStepBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_JpakeStep alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_JpakeStepBuilder*) clear {
+  self.result = [[ST_JpakeStep alloc] init];
+  return self;
+}
+- (ST_JpakeStepBuilder*) clone {
+  return [ST_JpakeStep builderWithPrototype:result];
+}
+- (ST_JpakeStep*) defaultInstance {
+  return [ST_JpakeStep defaultInstance];
+}
+- (ST_JpakeStep*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_JpakeStep*) buildPartial {
+  ST_JpakeStep* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_JpakeStepBuilder*) mergeFrom:(ST_JpakeStep*) other {
+  if (other == [ST_JpakeStep defaultInstance]) {
+    return self;
+  }
+  if (other.hasGx) {
+    [self setGx:other.gx];
+  }
+  if (other.hasGr) {
+    [self setGr:other.gr];
+  }
+  if (other.hasB) {
+    [self setB:other.b];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_JpakeStepBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_JpakeStepBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setGx:[input readData]];
+        break;
+      }
+      case 18: {
+        [self setGr:[input readData]];
+        break;
+      }
+      case 26: {
+        [self setB:[input readData]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasGx {
+  return result.hasGx;
+}
+- (NSData*) gx {
+  return result.gx;
+}
+- (ST_JpakeStepBuilder*) setGx:(NSData*) value {
+  result.hasGx = YES;
+  result.gx = value;
+  return self;
+}
+- (ST_JpakeStepBuilder*) clearGx {
+  result.hasGx = NO;
+  result.gx = [NSData data];
+  return self;
+}
+- (BOOL) hasGr {
+  return result.hasGr;
+}
+- (NSData*) gr {
+  return result.gr;
+}
+- (ST_JpakeStepBuilder*) setGr:(NSData*) value {
+  result.hasGr = YES;
+  result.gr = value;
+  return self;
+}
+- (ST_JpakeStepBuilder*) clearGr {
+  result.hasGr = NO;
+  result.gr = [NSData data];
+  return self;
+}
+- (BOOL) hasB {
+  return result.hasB;
+}
+- (NSData*) b {
+  return result.b;
+}
+- (ST_JpakeStepBuilder*) setB:(NSData*) value {
+  result.hasB = YES;
+  result.b = value;
+  return self;
+}
+- (ST_JpakeStepBuilder*) clearB {
+  result.hasB = NO;
+  result.b = [NSData data];
+  return self;
+}
+@end
+
+@interface ST_JpakeBegin ()
+@property (strong) ST_JpakeStep* astep1P1;
+@property (strong) ST_JpakeStep* astep1P2;
+@end
+
+@implementation ST_JpakeBegin
+
+- (BOOL) hasAstep1P1 {
+  return !!hasAstep1P1_;
+}
+- (void) setHasAstep1P1:(BOOL) value_ {
+  hasAstep1P1_ = !!value_;
+}
+@synthesize astep1P1;
+- (BOOL) hasAstep1P2 {
+  return !!hasAstep1P2_;
+}
+- (void) setHasAstep1P2:(BOOL) value_ {
+  hasAstep1P2_ = !!value_;
+}
+@synthesize astep1P2;
+- (id) init {
+  if ((self = [super init])) {
+    self.astep1P1 = [ST_JpakeStep defaultInstance];
+    self.astep1P2 = [ST_JpakeStep defaultInstance];
+  }
+  return self;
+}
+static ST_JpakeBegin* defaultST_JpakeBeginInstance = nil;
++ (void) initialize {
+  if (self == [ST_JpakeBegin class]) {
+    defaultST_JpakeBeginInstance = [[ST_JpakeBegin alloc] init];
+  }
+}
++ (ST_JpakeBegin*) defaultInstance {
+  return defaultST_JpakeBeginInstance;
+}
+- (ST_JpakeBegin*) defaultInstance {
+  return defaultST_JpakeBeginInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasAstep1P1) {
+    [output writeMessage:1 value:self.astep1P1];
+  }
+  if (self.hasAstep1P2) {
+    [output writeMessage:2 value:self.astep1P2];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasAstep1P1) {
+    size_ += computeMessageSize(1, self.astep1P1);
+  }
+  if (self.hasAstep1P2) {
+    size_ += computeMessageSize(2, self.astep1P2);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_JpakeBegin*) parseFromData:(NSData*) data {
+  return (ST_JpakeBegin*)[[[ST_JpakeBegin builder] mergeFromData:data] build];
+}
++ (ST_JpakeBegin*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeBegin*)[[[ST_JpakeBegin builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeBegin*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_JpakeBegin*)[[[ST_JpakeBegin builder] mergeFromInputStream:input] build];
+}
++ (ST_JpakeBegin*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeBegin*)[[[ST_JpakeBegin builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_JpakeBegin*)[[[ST_JpakeBegin builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_JpakeBegin*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeBegin*)[[[ST_JpakeBegin builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeBeginBuilder*) builder {
+  return [[ST_JpakeBeginBuilder alloc] init];
+}
++ (ST_JpakeBeginBuilder*) builderWithPrototype:(ST_JpakeBegin*) prototype {
+  return [[ST_JpakeBegin builder] mergeFrom:prototype];
+}
+- (ST_JpakeBeginBuilder*) builder {
+  return [ST_JpakeBegin builder];
+}
+- (ST_JpakeBeginBuilder*) toBuilder {
+  return [ST_JpakeBegin builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasAstep1P1) {
+    [output appendFormat:@"%@%@ {\n", indent, @"astep1P1"];
+    [self.astep1P1 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasAstep1P2) {
+    [output appendFormat:@"%@%@ {\n", indent, @"astep1P2"];
+    [self.astep1P2 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_JpakeBegin class]]) {
+    return NO;
+  }
+  ST_JpakeBegin *otherMessage = other;
+  return
+      self.hasAstep1P1 == otherMessage.hasAstep1P1 &&
+      (!self.hasAstep1P1 || [self.astep1P1 isEqual:otherMessage.astep1P1]) &&
+      self.hasAstep1P2 == otherMessage.hasAstep1P2 &&
+      (!self.hasAstep1P2 || [self.astep1P2 isEqual:otherMessage.astep1P2]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasAstep1P1) {
+    hashCode = hashCode * 31 + [self.astep1P1 hash];
+  }
+  if (self.hasAstep1P2) {
+    hashCode = hashCode * 31 + [self.astep1P2 hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ST_JpakeBeginBuilder()
+@property (strong) ST_JpakeBegin* result;
+@end
+
+@implementation ST_JpakeBeginBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_JpakeBegin alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_JpakeBeginBuilder*) clear {
+  self.result = [[ST_JpakeBegin alloc] init];
+  return self;
+}
+- (ST_JpakeBeginBuilder*) clone {
+  return [ST_JpakeBegin builderWithPrototype:result];
+}
+- (ST_JpakeBegin*) defaultInstance {
+  return [ST_JpakeBegin defaultInstance];
+}
+- (ST_JpakeBegin*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_JpakeBegin*) buildPartial {
+  ST_JpakeBegin* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_JpakeBeginBuilder*) mergeFrom:(ST_JpakeBegin*) other {
+  if (other == [ST_JpakeBegin defaultInstance]) {
+    return self;
+  }
+  if (other.hasAstep1P1) {
+    [self mergeAstep1P1:other.astep1P1];
+  }
+  if (other.hasAstep1P2) {
+    [self mergeAstep1P2:other.astep1P2];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_JpakeBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_JpakeBeginBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        ST_JpakeStepBuilder* subBuilder = [ST_JpakeStep builder];
+        if (self.hasAstep1P1) {
+          [subBuilder mergeFrom:self.astep1P1];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setAstep1P1:[subBuilder buildPartial]];
+        break;
+      }
+      case 18: {
+        ST_JpakeStepBuilder* subBuilder = [ST_JpakeStep builder];
+        if (self.hasAstep1P2) {
+          [subBuilder mergeFrom:self.astep1P2];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setAstep1P2:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasAstep1P1 {
+  return result.hasAstep1P1;
+}
+- (ST_JpakeStep*) astep1P1 {
+  return result.astep1P1;
+}
+- (ST_JpakeBeginBuilder*) setAstep1P1:(ST_JpakeStep*) value {
+  result.hasAstep1P1 = YES;
+  result.astep1P1 = value;
+  return self;
+}
+- (ST_JpakeBeginBuilder*) setAstep1P1Builder:(ST_JpakeStepBuilder*) builderForValue {
+  return [self setAstep1P1:[builderForValue build]];
+}
+- (ST_JpakeBeginBuilder*) mergeAstep1P1:(ST_JpakeStep*) value {
+  if (result.hasAstep1P1 &&
+      result.astep1P1 != [ST_JpakeStep defaultInstance]) {
+    result.astep1P1 =
+      [[[ST_JpakeStep builderWithPrototype:result.astep1P1] mergeFrom:value] buildPartial];
+  } else {
+    result.astep1P1 = value;
+  }
+  result.hasAstep1P1 = YES;
+  return self;
+}
+- (ST_JpakeBeginBuilder*) clearAstep1P1 {
+  result.hasAstep1P1 = NO;
+  result.astep1P1 = [ST_JpakeStep defaultInstance];
+  return self;
+}
+- (BOOL) hasAstep1P2 {
+  return result.hasAstep1P2;
+}
+- (ST_JpakeStep*) astep1P2 {
+  return result.astep1P2;
+}
+- (ST_JpakeBeginBuilder*) setAstep1P2:(ST_JpakeStep*) value {
+  result.hasAstep1P2 = YES;
+  result.astep1P2 = value;
+  return self;
+}
+- (ST_JpakeBeginBuilder*) setAstep1P2Builder:(ST_JpakeStepBuilder*) builderForValue {
+  return [self setAstep1P2:[builderForValue build]];
+}
+- (ST_JpakeBeginBuilder*) mergeAstep1P2:(ST_JpakeStep*) value {
+  if (result.hasAstep1P2 &&
+      result.astep1P2 != [ST_JpakeStep defaultInstance]) {
+    result.astep1P2 =
+      [[[ST_JpakeStep builderWithPrototype:result.astep1P2] mergeFrom:value] buildPartial];
+  } else {
+    result.astep1P2 = value;
+  }
+  result.hasAstep1P2 = YES;
+  return self;
+}
+- (ST_JpakeBeginBuilder*) clearAstep1P2 {
+  result.hasAstep1P2 = NO;
+  result.astep1P2 = [ST_JpakeStep defaultInstance];
+  return self;
+}
+@end
+
+@interface ST_JpakeResponse ()
+@property (strong) ST_JpakeStep* cstep1P1;
+@property (strong) ST_JpakeStep* cstep1P2;
+@property (strong) ST_JpakeStep* cstep2;
+@end
+
+@implementation ST_JpakeResponse
+
+- (BOOL) hasCstep1P1 {
+  return !!hasCstep1P1_;
+}
+- (void) setHasCstep1P1:(BOOL) value_ {
+  hasCstep1P1_ = !!value_;
+}
+@synthesize cstep1P1;
+- (BOOL) hasCstep1P2 {
+  return !!hasCstep1P2_;
+}
+- (void) setHasCstep1P2:(BOOL) value_ {
+  hasCstep1P2_ = !!value_;
+}
+@synthesize cstep1P2;
+- (BOOL) hasCstep2 {
+  return !!hasCstep2_;
+}
+- (void) setHasCstep2:(BOOL) value_ {
+  hasCstep2_ = !!value_;
+}
+@synthesize cstep2;
+- (id) init {
+  if ((self = [super init])) {
+    self.cstep1P1 = [ST_JpakeStep defaultInstance];
+    self.cstep1P2 = [ST_JpakeStep defaultInstance];
+    self.cstep2 = [ST_JpakeStep defaultInstance];
+  }
+  return self;
+}
+static ST_JpakeResponse* defaultST_JpakeResponseInstance = nil;
++ (void) initialize {
+  if (self == [ST_JpakeResponse class]) {
+    defaultST_JpakeResponseInstance = [[ST_JpakeResponse alloc] init];
+  }
+}
++ (ST_JpakeResponse*) defaultInstance {
+  return defaultST_JpakeResponseInstance;
+}
+- (ST_JpakeResponse*) defaultInstance {
+  return defaultST_JpakeResponseInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasCstep1P1) {
+    [output writeMessage:1 value:self.cstep1P1];
+  }
+  if (self.hasCstep1P2) {
+    [output writeMessage:2 value:self.cstep1P2];
+  }
+  if (self.hasCstep2) {
+    [output writeMessage:3 value:self.cstep2];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasCstep1P1) {
+    size_ += computeMessageSize(1, self.cstep1P1);
+  }
+  if (self.hasCstep1P2) {
+    size_ += computeMessageSize(2, self.cstep1P2);
+  }
+  if (self.hasCstep2) {
+    size_ += computeMessageSize(3, self.cstep2);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_JpakeResponse*) parseFromData:(NSData*) data {
+  return (ST_JpakeResponse*)[[[ST_JpakeResponse builder] mergeFromData:data] build];
+}
++ (ST_JpakeResponse*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeResponse*)[[[ST_JpakeResponse builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeResponse*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_JpakeResponse*)[[[ST_JpakeResponse builder] mergeFromInputStream:input] build];
+}
++ (ST_JpakeResponse*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeResponse*)[[[ST_JpakeResponse builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeResponse*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_JpakeResponse*)[[[ST_JpakeResponse builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_JpakeResponse*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_JpakeResponse*)[[[ST_JpakeResponse builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_JpakeResponseBuilder*) builder {
+  return [[ST_JpakeResponseBuilder alloc] init];
+}
++ (ST_JpakeResponseBuilder*) builderWithPrototype:(ST_JpakeResponse*) prototype {
+  return [[ST_JpakeResponse builder] mergeFrom:prototype];
+}
+- (ST_JpakeResponseBuilder*) builder {
+  return [ST_JpakeResponse builder];
+}
+- (ST_JpakeResponseBuilder*) toBuilder {
+  return [ST_JpakeResponse builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasCstep1P1) {
+    [output appendFormat:@"%@%@ {\n", indent, @"cstep1P1"];
+    [self.cstep1P1 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasCstep1P2) {
+    [output appendFormat:@"%@%@ {\n", indent, @"cstep1P2"];
+    [self.cstep1P2 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasCstep2) {
+    [output appendFormat:@"%@%@ {\n", indent, @"cstep2"];
+    [self.cstep2 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_JpakeResponse class]]) {
+    return NO;
+  }
+  ST_JpakeResponse *otherMessage = other;
+  return
+      self.hasCstep1P1 == otherMessage.hasCstep1P1 &&
+      (!self.hasCstep1P1 || [self.cstep1P1 isEqual:otherMessage.cstep1P1]) &&
+      self.hasCstep1P2 == otherMessage.hasCstep1P2 &&
+      (!self.hasCstep1P2 || [self.cstep1P2 isEqual:otherMessage.cstep1P2]) &&
+      self.hasCstep2 == otherMessage.hasCstep2 &&
+      (!self.hasCstep2 || [self.cstep2 isEqual:otherMessage.cstep2]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasCstep1P1) {
+    hashCode = hashCode * 31 + [self.cstep1P1 hash];
+  }
+  if (self.hasCstep1P2) {
+    hashCode = hashCode * 31 + [self.cstep1P2 hash];
+  }
+  if (self.hasCstep2) {
+    hashCode = hashCode * 31 + [self.cstep2 hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ST_JpakeResponseBuilder()
+@property (strong) ST_JpakeResponse* result;
+@end
+
+@implementation ST_JpakeResponseBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_JpakeResponse alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_JpakeResponseBuilder*) clear {
+  self.result = [[ST_JpakeResponse alloc] init];
+  return self;
+}
+- (ST_JpakeResponseBuilder*) clone {
+  return [ST_JpakeResponse builderWithPrototype:result];
+}
+- (ST_JpakeResponse*) defaultInstance {
+  return [ST_JpakeResponse defaultInstance];
+}
+- (ST_JpakeResponse*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_JpakeResponse*) buildPartial {
+  ST_JpakeResponse* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_JpakeResponseBuilder*) mergeFrom:(ST_JpakeResponse*) other {
+  if (other == [ST_JpakeResponse defaultInstance]) {
+    return self;
+  }
+  if (other.hasCstep1P1) {
+    [self mergeCstep1P1:other.cstep1P1];
+  }
+  if (other.hasCstep1P2) {
+    [self mergeCstep1P2:other.cstep1P2];
+  }
+  if (other.hasCstep2) {
+    [self mergeCstep2:other.cstep2];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_JpakeResponseBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_JpakeResponseBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        ST_JpakeStepBuilder* subBuilder = [ST_JpakeStep builder];
+        if (self.hasCstep1P1) {
+          [subBuilder mergeFrom:self.cstep1P1];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setCstep1P1:[subBuilder buildPartial]];
+        break;
+      }
+      case 18: {
+        ST_JpakeStepBuilder* subBuilder = [ST_JpakeStep builder];
+        if (self.hasCstep1P2) {
+          [subBuilder mergeFrom:self.cstep1P2];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setCstep1P2:[subBuilder buildPartial]];
+        break;
+      }
+      case 26: {
+        ST_JpakeStepBuilder* subBuilder = [ST_JpakeStep builder];
+        if (self.hasCstep2) {
+          [subBuilder mergeFrom:self.cstep2];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setCstep2:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasCstep1P1 {
+  return result.hasCstep1P1;
+}
+- (ST_JpakeStep*) cstep1P1 {
+  return result.cstep1P1;
+}
+- (ST_JpakeResponseBuilder*) setCstep1P1:(ST_JpakeStep*) value {
+  result.hasCstep1P1 = YES;
+  result.cstep1P1 = value;
+  return self;
+}
+- (ST_JpakeResponseBuilder*) setCstep1P1Builder:(ST_JpakeStepBuilder*) builderForValue {
+  return [self setCstep1P1:[builderForValue build]];
+}
+- (ST_JpakeResponseBuilder*) mergeCstep1P1:(ST_JpakeStep*) value {
+  if (result.hasCstep1P1 &&
+      result.cstep1P1 != [ST_JpakeStep defaultInstance]) {
+    result.cstep1P1 =
+      [[[ST_JpakeStep builderWithPrototype:result.cstep1P1] mergeFrom:value] buildPartial];
+  } else {
+    result.cstep1P1 = value;
+  }
+  result.hasCstep1P1 = YES;
+  return self;
+}
+- (ST_JpakeResponseBuilder*) clearCstep1P1 {
+  result.hasCstep1P1 = NO;
+  result.cstep1P1 = [ST_JpakeStep defaultInstance];
+  return self;
+}
+- (BOOL) hasCstep1P2 {
+  return result.hasCstep1P2;
+}
+- (ST_JpakeStep*) cstep1P2 {
+  return result.cstep1P2;
+}
+- (ST_JpakeResponseBuilder*) setCstep1P2:(ST_JpakeStep*) value {
+  result.hasCstep1P2 = YES;
+  result.cstep1P2 = value;
+  return self;
+}
+- (ST_JpakeResponseBuilder*) setCstep1P2Builder:(ST_JpakeStepBuilder*) builderForValue {
+  return [self setCstep1P2:[builderForValue build]];
+}
+- (ST_JpakeResponseBuilder*) mergeCstep1P2:(ST_JpakeStep*) value {
+  if (result.hasCstep1P2 &&
+      result.cstep1P2 != [ST_JpakeStep defaultInstance]) {
+    result.cstep1P2 =
+      [[[ST_JpakeStep builderWithPrototype:result.cstep1P2] mergeFrom:value] buildPartial];
+  } else {
+    result.cstep1P2 = value;
+  }
+  result.hasCstep1P2 = YES;
+  return self;
+}
+- (ST_JpakeResponseBuilder*) clearCstep1P2 {
+  result.hasCstep1P2 = NO;
+  result.cstep1P2 = [ST_JpakeStep defaultInstance];
+  return self;
+}
+- (BOOL) hasCstep2 {
+  return result.hasCstep2;
+}
+- (ST_JpakeStep*) cstep2 {
+  return result.cstep2;
+}
+- (ST_JpakeResponseBuilder*) setCstep2:(ST_JpakeStep*) value {
+  result.hasCstep2 = YES;
+  result.cstep2 = value;
+  return self;
+}
+- (ST_JpakeResponseBuilder*) setCstep2Builder:(ST_JpakeStepBuilder*) builderForValue {
+  return [self setCstep2:[builderForValue build]];
+}
+- (ST_JpakeResponseBuilder*) mergeCstep2:(ST_JpakeStep*) value {
+  if (result.hasCstep2 &&
+      result.cstep2 != [ST_JpakeStep defaultInstance]) {
+    result.cstep2 =
+      [[[ST_JpakeStep builderWithPrototype:result.cstep2] mergeFrom:value] buildPartial];
+  } else {
+    result.cstep2 = value;
+  }
+  result.hasCstep2 = YES;
+  return self;
+}
+- (ST_JpakeResponseBuilder*) clearCstep2 {
+  result.hasCstep2 = NO;
+  result.cstep2 = [ST_JpakeStep defaultInstance];
+  return self;
+}
+@end
+
+@interface ST_InitSetup ()
+@property (strong) ST_JpakeStep* astep2;
+@property (strong) NSData* step3A;
+@end
+
+@implementation ST_InitSetup
+
+- (BOOL) hasAstep2 {
+  return !!hasAstep2_;
+}
+- (void) setHasAstep2:(BOOL) value_ {
+  hasAstep2_ = !!value_;
+}
+@synthesize astep2;
+- (BOOL) hasStep3A {
+  return !!hasStep3A_;
+}
+- (void) setHasStep3A:(BOOL) value_ {
+  hasStep3A_ = !!value_;
+}
+@synthesize step3A;
+- (id) init {
+  if ((self = [super init])) {
+    self.astep2 = [ST_JpakeStep defaultInstance];
+    self.step3A = [NSData data];
+  }
+  return self;
+}
+static ST_InitSetup* defaultST_InitSetupInstance = nil;
++ (void) initialize {
+  if (self == [ST_InitSetup class]) {
+    defaultST_InitSetupInstance = [[ST_InitSetup alloc] init];
+  }
+}
++ (ST_InitSetup*) defaultInstance {
+  return defaultST_InitSetupInstance;
+}
+- (ST_InitSetup*) defaultInstance {
+  return defaultST_InitSetupInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasAstep2) {
+    [output writeMessage:1 value:self.astep2];
+  }
+  if (self.hasStep3A) {
+    [output writeData:2 value:self.step3A];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasAstep2) {
+    size_ += computeMessageSize(1, self.astep2);
+  }
+  if (self.hasStep3A) {
+    size_ += computeDataSize(2, self.step3A);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_InitSetup*) parseFromData:(NSData*) data {
+  return (ST_InitSetup*)[[[ST_InitSetup builder] mergeFromData:data] build];
+}
++ (ST_InitSetup*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_InitSetup*)[[[ST_InitSetup builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_InitSetup*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_InitSetup*)[[[ST_InitSetup builder] mergeFromInputStream:input] build];
+}
++ (ST_InitSetup*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_InitSetup*)[[[ST_InitSetup builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_InitSetup*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_InitSetup*)[[[ST_InitSetup builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_InitSetup*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_InitSetup*)[[[ST_InitSetup builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_InitSetupBuilder*) builder {
+  return [[ST_InitSetupBuilder alloc] init];
+}
++ (ST_InitSetupBuilder*) builderWithPrototype:(ST_InitSetup*) prototype {
+  return [[ST_InitSetup builder] mergeFrom:prototype];
+}
+- (ST_InitSetupBuilder*) builder {
+  return [ST_InitSetup builder];
+}
+- (ST_InitSetupBuilder*) toBuilder {
+  return [ST_InitSetup builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasAstep2) {
+    [output appendFormat:@"%@%@ {\n", indent, @"astep2"];
+    [self.astep2 writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasStep3A) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"step3A", self.step3A];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_InitSetup class]]) {
+    return NO;
+  }
+  ST_InitSetup *otherMessage = other;
+  return
+      self.hasAstep2 == otherMessage.hasAstep2 &&
+      (!self.hasAstep2 || [self.astep2 isEqual:otherMessage.astep2]) &&
+      self.hasStep3A == otherMessage.hasStep3A &&
+      (!self.hasStep3A || [self.step3A isEqual:otherMessage.step3A]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasAstep2) {
+    hashCode = hashCode * 31 + [self.astep2 hash];
+  }
+  if (self.hasStep3A) {
+    hashCode = hashCode * 31 + [self.step3A hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ST_InitSetupBuilder()
+@property (strong) ST_InitSetup* result;
+@end
+
+@implementation ST_InitSetupBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_InitSetup alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_InitSetupBuilder*) clear {
+  self.result = [[ST_InitSetup alloc] init];
+  return self;
+}
+- (ST_InitSetupBuilder*) clone {
+  return [ST_InitSetup builderWithPrototype:result];
+}
+- (ST_InitSetup*) defaultInstance {
+  return [ST_InitSetup defaultInstance];
+}
+- (ST_InitSetup*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_InitSetup*) buildPartial {
+  ST_InitSetup* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_InitSetupBuilder*) mergeFrom:(ST_InitSetup*) other {
+  if (other == [ST_InitSetup defaultInstance]) {
+    return self;
+  }
+  if (other.hasAstep2) {
+    [self mergeAstep2:other.astep2];
+  }
+  if (other.hasStep3A) {
+    [self setStep3A:other.step3A];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_InitSetupBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_InitSetupBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        ST_JpakeStepBuilder* subBuilder = [ST_JpakeStep builder];
+        if (self.hasAstep2) {
+          [subBuilder mergeFrom:self.astep2];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setAstep2:[subBuilder buildPartial]];
+        break;
+      }
+      case 18: {
+        [self setStep3A:[input readData]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasAstep2 {
+  return result.hasAstep2;
+}
+- (ST_JpakeStep*) astep2 {
+  return result.astep2;
+}
+- (ST_InitSetupBuilder*) setAstep2:(ST_JpakeStep*) value {
+  result.hasAstep2 = YES;
+  result.astep2 = value;
+  return self;
+}
+- (ST_InitSetupBuilder*) setAstep2Builder:(ST_JpakeStepBuilder*) builderForValue {
+  return [self setAstep2:[builderForValue build]];
+}
+- (ST_InitSetupBuilder*) mergeAstep2:(ST_JpakeStep*) value {
+  if (result.hasAstep2 &&
+      result.astep2 != [ST_JpakeStep defaultInstance]) {
+    result.astep2 =
+      [[[ST_JpakeStep builderWithPrototype:result.astep2] mergeFrom:value] buildPartial];
+  } else {
+    result.astep2 = value;
+  }
+  result.hasAstep2 = YES;
+  return self;
+}
+- (ST_InitSetupBuilder*) clearAstep2 {
+  result.hasAstep2 = NO;
+  result.astep2 = [ST_JpakeStep defaultInstance];
+  return self;
+}
+- (BOOL) hasStep3A {
+  return result.hasStep3A;
+}
+- (NSData*) step3A {
+  return result.step3A;
+}
+- (ST_InitSetupBuilder*) setStep3A:(NSData*) value {
+  result.hasStep3A = YES;
+  result.step3A = value;
+  return self;
+}
+- (ST_InitSetupBuilder*) clearStep3A {
+  result.hasStep3A = NO;
+  result.step3A = [NSData data];
+  return self;
+}
+@end
+
+@interface ST_DeviceInfo ()
+@property (strong) NSData* nonce;
+@property (strong) NSData* token;
+@property (strong) NSData* flags;
+@property (strong) NSData* step3B;
+@end
+
+@implementation ST_DeviceInfo
+
+- (BOOL) hasNonce {
+  return !!hasNonce_;
+}
+- (void) setHasNonce:(BOOL) value_ {
+  hasNonce_ = !!value_;
+}
+@synthesize nonce;
+- (BOOL) hasToken {
+  return !!hasToken_;
+}
+- (void) setHasToken:(BOOL) value_ {
+  hasToken_ = !!value_;
+}
+@synthesize token;
+- (BOOL) hasFlags {
+  return !!hasFlags_;
+}
+- (void) setHasFlags:(BOOL) value_ {
+  hasFlags_ = !!value_;
+}
+@synthesize flags;
+- (BOOL) hasStep3B {
+  return !!hasStep3B_;
+}
+- (void) setHasStep3B:(BOOL) value_ {
+  hasStep3B_ = !!value_;
+}
+@synthesize step3B;
+- (id) init {
+  if ((self = [super init])) {
+    self.nonce = [NSData data];
+    self.token = [NSData data];
+    self.flags = [NSData data];
+    self.step3B = [NSData data];
+  }
+  return self;
+}
+static ST_DeviceInfo* defaultST_DeviceInfoInstance = nil;
++ (void) initialize {
+  if (self == [ST_DeviceInfo class]) {
+    defaultST_DeviceInfoInstance = [[ST_DeviceInfo alloc] init];
+  }
+}
++ (ST_DeviceInfo*) defaultInstance {
+  return defaultST_DeviceInfoInstance;
+}
+- (ST_DeviceInfo*) defaultInstance {
+  return defaultST_DeviceInfoInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasNonce) {
+    [output writeData:1 value:self.nonce];
+  }
+  if (self.hasToken) {
+    [output writeData:2 value:self.token];
+  }
+  if (self.hasFlags) {
+    [output writeData:3 value:self.flags];
+  }
+  if (self.hasStep3B) {
+    [output writeData:4 value:self.step3B];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasNonce) {
+    size_ += computeDataSize(1, self.nonce);
+  }
+  if (self.hasToken) {
+    size_ += computeDataSize(2, self.token);
+  }
+  if (self.hasFlags) {
+    size_ += computeDataSize(3, self.flags);
+  }
+  if (self.hasStep3B) {
+    size_ += computeDataSize(4, self.step3B);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_DeviceInfo*) parseFromData:(NSData*) data {
+  return (ST_DeviceInfo*)[[[ST_DeviceInfo builder] mergeFromData:data] build];
+}
++ (ST_DeviceInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_DeviceInfo*)[[[ST_DeviceInfo builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_DeviceInfo*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_DeviceInfo*)[[[ST_DeviceInfo builder] mergeFromInputStream:input] build];
+}
++ (ST_DeviceInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_DeviceInfo*)[[[ST_DeviceInfo builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_DeviceInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_DeviceInfo*)[[[ST_DeviceInfo builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_DeviceInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_DeviceInfo*)[[[ST_DeviceInfo builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_DeviceInfoBuilder*) builder {
+  return [[ST_DeviceInfoBuilder alloc] init];
+}
++ (ST_DeviceInfoBuilder*) builderWithPrototype:(ST_DeviceInfo*) prototype {
+  return [[ST_DeviceInfo builder] mergeFrom:prototype];
+}
+- (ST_DeviceInfoBuilder*) builder {
+  return [ST_DeviceInfo builder];
+}
+- (ST_DeviceInfoBuilder*) toBuilder {
+  return [ST_DeviceInfo builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasNonce) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"nonce", self.nonce];
+  }
+  if (self.hasToken) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"token", self.token];
+  }
+  if (self.hasFlags) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"flags", self.flags];
+  }
+  if (self.hasStep3B) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"step3B", self.step3B];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_DeviceInfo class]]) {
+    return NO;
+  }
+  ST_DeviceInfo *otherMessage = other;
+  return
+      self.hasNonce == otherMessage.hasNonce &&
+      (!self.hasNonce || [self.nonce isEqual:otherMessage.nonce]) &&
+      self.hasToken == otherMessage.hasToken &&
+      (!self.hasToken || [self.token isEqual:otherMessage.token]) &&
+      self.hasFlags == otherMessage.hasFlags &&
+      (!self.hasFlags || [self.flags isEqual:otherMessage.flags]) &&
+      self.hasStep3B == otherMessage.hasStep3B &&
+      (!self.hasStep3B || [self.step3B isEqual:otherMessage.step3B]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasNonce) {
+    hashCode = hashCode * 31 + [self.nonce hash];
+  }
+  if (self.hasToken) {
+    hashCode = hashCode * 31 + [self.token hash];
+  }
+  if (self.hasFlags) {
+    hashCode = hashCode * 31 + [self.flags hash];
+  }
+  if (self.hasStep3B) {
+    hashCode = hashCode * 31 + [self.step3B hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ST_DeviceInfoBuilder()
+@property (strong) ST_DeviceInfo* result;
+@end
+
+@implementation ST_DeviceInfoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_DeviceInfo alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_DeviceInfoBuilder*) clear {
+  self.result = [[ST_DeviceInfo alloc] init];
+  return self;
+}
+- (ST_DeviceInfoBuilder*) clone {
+  return [ST_DeviceInfo builderWithPrototype:result];
+}
+- (ST_DeviceInfo*) defaultInstance {
+  return [ST_DeviceInfo defaultInstance];
+}
+- (ST_DeviceInfo*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_DeviceInfo*) buildPartial {
+  ST_DeviceInfo* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_DeviceInfoBuilder*) mergeFrom:(ST_DeviceInfo*) other {
+  if (other == [ST_DeviceInfo defaultInstance]) {
+    return self;
+  }
+  if (other.hasNonce) {
+    [self setNonce:other.nonce];
+  }
+  if (other.hasToken) {
+    [self setToken:other.token];
+  }
+  if (other.hasFlags) {
+    [self setFlags:other.flags];
+  }
+  if (other.hasStep3B) {
+    [self setStep3B:other.step3B];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_DeviceInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_DeviceInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setNonce:[input readData]];
+        break;
+      }
+      case 18: {
+        [self setToken:[input readData]];
+        break;
+      }
+      case 26: {
+        [self setFlags:[input readData]];
+        break;
+      }
+      case 34: {
+        [self setStep3B:[input readData]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasNonce {
+  return result.hasNonce;
+}
+- (NSData*) nonce {
+  return result.nonce;
+}
+- (ST_DeviceInfoBuilder*) setNonce:(NSData*) value {
+  result.hasNonce = YES;
+  result.nonce = value;
+  return self;
+}
+- (ST_DeviceInfoBuilder*) clearNonce {
+  result.hasNonce = NO;
+  result.nonce = [NSData data];
+  return self;
+}
+- (BOOL) hasToken {
+  return result.hasToken;
+}
+- (NSData*) token {
+  return result.token;
+}
+- (ST_DeviceInfoBuilder*) setToken:(NSData*) value {
+  result.hasToken = YES;
+  result.token = value;
+  return self;
+}
+- (ST_DeviceInfoBuilder*) clearToken {
+  result.hasToken = NO;
+  result.token = [NSData data];
+  return self;
+}
+- (BOOL) hasFlags {
+  return result.hasFlags;
+}
+- (NSData*) flags {
+  return result.flags;
+}
+- (ST_DeviceInfoBuilder*) setFlags:(NSData*) value {
+  result.hasFlags = YES;
+  result.flags = value;
+  return self;
+}
+- (ST_DeviceInfoBuilder*) clearFlags {
+  result.hasFlags = NO;
+  result.flags = [NSData data];
+  return self;
+}
+- (BOOL) hasStep3B {
+  return result.hasStep3B;
+}
+- (NSData*) step3B {
+  return result.step3B;
+}
+- (ST_DeviceInfoBuilder*) setStep3B:(NSData*) value {
+  result.hasStep3B = YES;
+  result.step3B = value;
+  return self;
+}
+- (ST_DeviceInfoBuilder*) clearStep3B {
+  result.hasStep3B = NO;
+  result.step3B = [NSData data];
+  return self;
+}
+@end
+
+@interface ST_WifiScan ()
+@property (strong) NSData* authTag;
+@end
+
+@implementation ST_WifiScan
+
+- (BOOL) hasAuthTag {
+  return !!hasAuthTag_;
+}
+- (void) setHasAuthTag:(BOOL) value_ {
+  hasAuthTag_ = !!value_;
+}
+@synthesize authTag;
+- (id) init {
+  if ((self = [super init])) {
+    self.authTag = [NSData data];
+  }
+  return self;
+}
+static ST_WifiScan* defaultST_WifiScanInstance = nil;
++ (void) initialize {
+  if (self == [ST_WifiScan class]) {
+    defaultST_WifiScanInstance = [[ST_WifiScan alloc] init];
+  }
+}
++ (ST_WifiScan*) defaultInstance {
+  return defaultST_WifiScanInstance;
+}
+- (ST_WifiScan*) defaultInstance {
+  return defaultST_WifiScanInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasAuthTag) {
+    [output writeData:1 value:self.authTag];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasAuthTag) {
+    size_ += computeDataSize(1, self.authTag);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_WifiScan*) parseFromData:(NSData*) data {
+  return (ST_WifiScan*)[[[ST_WifiScan builder] mergeFromData:data] build];
+}
++ (ST_WifiScan*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiScan*)[[[ST_WifiScan builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiScan*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_WifiScan*)[[[ST_WifiScan builder] mergeFromInputStream:input] build];
+}
++ (ST_WifiScan*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiScan*)[[[ST_WifiScan builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiScan*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_WifiScan*)[[[ST_WifiScan builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_WifiScan*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiScan*)[[[ST_WifiScan builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiScanBuilder*) builder {
+  return [[ST_WifiScanBuilder alloc] init];
+}
++ (ST_WifiScanBuilder*) builderWithPrototype:(ST_WifiScan*) prototype {
+  return [[ST_WifiScan builder] mergeFrom:prototype];
+}
+- (ST_WifiScanBuilder*) builder {
+  return [ST_WifiScan builder];
+}
+- (ST_WifiScanBuilder*) toBuilder {
+  return [ST_WifiScan builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasAuthTag) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"authTag", self.authTag];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_WifiScan class]]) {
+    return NO;
+  }
+  ST_WifiScan *otherMessage = other;
+  return
+      self.hasAuthTag == otherMessage.hasAuthTag &&
+      (!self.hasAuthTag || [self.authTag isEqual:otherMessage.authTag]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasAuthTag) {
+    hashCode = hashCode * 31 + [self.authTag hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ST_WifiScanBuilder()
+@property (strong) ST_WifiScan* result;
+@end
+
+@implementation ST_WifiScanBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_WifiScan alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_WifiScanBuilder*) clear {
+  self.result = [[ST_WifiScan alloc] init];
+  return self;
+}
+- (ST_WifiScanBuilder*) clone {
+  return [ST_WifiScan builderWithPrototype:result];
+}
+- (ST_WifiScan*) defaultInstance {
+  return [ST_WifiScan defaultInstance];
+}
+- (ST_WifiScan*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_WifiScan*) buildPartial {
+  ST_WifiScan* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_WifiScanBuilder*) mergeFrom:(ST_WifiScan*) other {
+  if (other == [ST_WifiScan defaultInstance]) {
+    return self;
+  }
+  if (other.hasAuthTag) {
+    [self setAuthTag:other.authTag];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_WifiScanBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_WifiScanBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setAuthTag:[input readData]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasAuthTag {
+  return result.hasAuthTag;
+}
+- (NSData*) authTag {
+  return result.authTag;
+}
+- (ST_WifiScanBuilder*) setAuthTag:(NSData*) value {
+  result.hasAuthTag = YES;
+  result.authTag = value;
+  return self;
+}
+- (ST_WifiScanBuilder*) clearAuthTag {
+  result.hasAuthTag = NO;
+  result.authTag = [NSData data];
+  return self;
+}
+@end
+
+@interface ST_WifiConnect ()
+@property (strong) NSString* bssid;
+@property (strong) NSString* ssid;
+@property (strong) NSData* encryptedPassword;
+@property ST_WifiConnectNetworkSecurityType type;
+@property BOOL isManual;
+@property (strong) NSData* authTag;
+@property (strong) NSData* jpakeHmac;
+@end
+
+@implementation ST_WifiConnect
+
+- (BOOL) hasBssid {
+  return !!hasBssid_;
+}
+- (void) setHasBssid:(BOOL) value_ {
+  hasBssid_ = !!value_;
+}
+@synthesize bssid;
+- (BOOL) hasSsid {
+  return !!hasSsid_;
+}
+- (void) setHasSsid:(BOOL) value_ {
+  hasSsid_ = !!value_;
+}
+@synthesize ssid;
+- (BOOL) hasEncryptedPassword {
+  return !!hasEncryptedPassword_;
+}
+- (void) setHasEncryptedPassword:(BOOL) value_ {
+  hasEncryptedPassword_ = !!value_;
+}
+@synthesize encryptedPassword;
+- (BOOL) hasType {
+  return !!hasType_;
+}
+- (void) setHasType:(BOOL) value_ {
+  hasType_ = !!value_;
+}
+@synthesize type;
+- (BOOL) hasIsManual {
+  return !!hasIsManual_;
+}
+- (void) setHasIsManual:(BOOL) value_ {
+  hasIsManual_ = !!value_;
+}
+- (BOOL) isManual {
+  return !!isManual_;
+}
+- (void) setIsManual:(BOOL) value_ {
+  isManual_ = !!value_;
+}
+- (BOOL) hasAuthTag {
+  return !!hasAuthTag_;
+}
+- (void) setHasAuthTag:(BOOL) value_ {
+  hasAuthTag_ = !!value_;
+}
+@synthesize authTag;
+- (BOOL) hasJpakeHmac {
+  return !!hasJpakeHmac_;
+}
+- (void) setHasJpakeHmac:(BOOL) value_ {
+  hasJpakeHmac_ = !!value_;
+}
+@synthesize jpakeHmac;
+- (id) init {
+  if ((self = [super init])) {
+    self.bssid = @"";
+    self.ssid = @"";
+    self.encryptedPassword = [NSData data];
+    self.type = ST_WifiConnectNetworkSecurityTypeNone;
+    self.isManual = NO;
+    self.authTag = [NSData data];
+    self.jpakeHmac = [NSData data];
+  }
+  return self;
+}
+static ST_WifiConnect* defaultST_WifiConnectInstance = nil;
++ (void) initialize {
+  if (self == [ST_WifiConnect class]) {
+    defaultST_WifiConnectInstance = [[ST_WifiConnect alloc] init];
+  }
+}
++ (ST_WifiConnect*) defaultInstance {
+  return defaultST_WifiConnectInstance;
+}
+- (ST_WifiConnect*) defaultInstance {
+  return defaultST_WifiConnectInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasType) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasBssid) {
+    [output writeString:1 value:self.bssid];
+  }
+  if (self.hasSsid) {
+    [output writeString:2 value:self.ssid];
+  }
+  if (self.hasEncryptedPassword) {
+    [output writeData:3 value:self.encryptedPassword];
+  }
+  if (self.hasType) {
+    [output writeEnum:4 value:self.type];
+  }
+  if (self.hasIsManual) {
+    [output writeBool:5 value:self.isManual];
+  }
+  if (self.hasAuthTag) {
+    [output writeData:6 value:self.authTag];
+  }
+  if (self.hasJpakeHmac) {
+    [output writeData:7 value:self.jpakeHmac];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasBssid) {
+    size_ += computeStringSize(1, self.bssid);
+  }
+  if (self.hasSsid) {
+    size_ += computeStringSize(2, self.ssid);
+  }
+  if (self.hasEncryptedPassword) {
+    size_ += computeDataSize(3, self.encryptedPassword);
+  }
+  if (self.hasType) {
+    size_ += computeEnumSize(4, self.type);
+  }
+  if (self.hasIsManual) {
+    size_ += computeBoolSize(5, self.isManual);
+  }
+  if (self.hasAuthTag) {
+    size_ += computeDataSize(6, self.authTag);
+  }
+  if (self.hasJpakeHmac) {
+    size_ += computeDataSize(7, self.jpakeHmac);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_WifiConnect*) parseFromData:(NSData*) data {
+  return (ST_WifiConnect*)[[[ST_WifiConnect builder] mergeFromData:data] build];
+}
++ (ST_WifiConnect*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiConnect*)[[[ST_WifiConnect builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiConnect*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_WifiConnect*)[[[ST_WifiConnect builder] mergeFromInputStream:input] build];
+}
++ (ST_WifiConnect*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiConnect*)[[[ST_WifiConnect builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiConnect*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_WifiConnect*)[[[ST_WifiConnect builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_WifiConnect*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiConnect*)[[[ST_WifiConnect builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiConnectBuilder*) builder {
+  return [[ST_WifiConnectBuilder alloc] init];
+}
++ (ST_WifiConnectBuilder*) builderWithPrototype:(ST_WifiConnect*) prototype {
+  return [[ST_WifiConnect builder] mergeFrom:prototype];
+}
+- (ST_WifiConnectBuilder*) builder {
+  return [ST_WifiConnect builder];
+}
+- (ST_WifiConnectBuilder*) toBuilder {
+  return [ST_WifiConnect builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasBssid) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"bssid", self.bssid];
+  }
+  if (self.hasSsid) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"ssid", self.ssid];
+  }
+  if (self.hasEncryptedPassword) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"encryptedPassword", self.encryptedPassword];
+  }
+  if (self.hasType) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"type", self.type];
+  }
+  if (self.hasIsManual) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"isManual", [NSNumber numberWithBool:self.isManual]];
+  }
+  if (self.hasAuthTag) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"authTag", self.authTag];
+  }
+  if (self.hasJpakeHmac) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"jpakeHmac", self.jpakeHmac];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_WifiConnect class]]) {
+    return NO;
+  }
+  ST_WifiConnect *otherMessage = other;
+  return
+      self.hasBssid == otherMessage.hasBssid &&
+      (!self.hasBssid || [self.bssid isEqual:otherMessage.bssid]) &&
+      self.hasSsid == otherMessage.hasSsid &&
+      (!self.hasSsid || [self.ssid isEqual:otherMessage.ssid]) &&
+      self.hasEncryptedPassword == otherMessage.hasEncryptedPassword &&
+      (!self.hasEncryptedPassword || [self.encryptedPassword isEqual:otherMessage.encryptedPassword]) &&
+      self.hasType == otherMessage.hasType &&
+      (!self.hasType || self.type == otherMessage.type) &&
+      self.hasIsManual == otherMessage.hasIsManual &&
+      (!self.hasIsManual || self.isManual == otherMessage.isManual) &&
+      self.hasAuthTag == otherMessage.hasAuthTag &&
+      (!self.hasAuthTag || [self.authTag isEqual:otherMessage.authTag]) &&
+      self.hasJpakeHmac == otherMessage.hasJpakeHmac &&
+      (!self.hasJpakeHmac || [self.jpakeHmac isEqual:otherMessage.jpakeHmac]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasBssid) {
+    hashCode = hashCode * 31 + [self.bssid hash];
+  }
+  if (self.hasSsid) {
+    hashCode = hashCode * 31 + [self.ssid hash];
+  }
+  if (self.hasEncryptedPassword) {
+    hashCode = hashCode * 31 + [self.encryptedPassword hash];
+  }
+  if (self.hasType) {
+    hashCode = hashCode * 31 + self.type;
+  }
+  if (self.hasIsManual) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.isManual] hash];
+  }
+  if (self.hasAuthTag) {
+    hashCode = hashCode * 31 + [self.authTag hash];
+  }
+  if (self.hasJpakeHmac) {
+    hashCode = hashCode * 31 + [self.jpakeHmac hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL ST_WifiConnectNetworkSecurityTypeIsValidValue(ST_WifiConnectNetworkSecurityType value) {
+  switch (value) {
+    case ST_WifiConnectNetworkSecurityTypeNone:
+    case ST_WifiConnectNetworkSecurityTypeWep:
+    case ST_WifiConnectNetworkSecurityTypeWpaPersonal:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface ST_WifiConnectBuilder()
+@property (strong) ST_WifiConnect* result;
+@end
+
+@implementation ST_WifiConnectBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_WifiConnect alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_WifiConnectBuilder*) clear {
+  self.result = [[ST_WifiConnect alloc] init];
+  return self;
+}
+- (ST_WifiConnectBuilder*) clone {
+  return [ST_WifiConnect builderWithPrototype:result];
+}
+- (ST_WifiConnect*) defaultInstance {
+  return [ST_WifiConnect defaultInstance];
+}
+- (ST_WifiConnect*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_WifiConnect*) buildPartial {
+  ST_WifiConnect* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_WifiConnectBuilder*) mergeFrom:(ST_WifiConnect*) other {
+  if (other == [ST_WifiConnect defaultInstance]) {
+    return self;
+  }
+  if (other.hasBssid) {
+    [self setBssid:other.bssid];
+  }
+  if (other.hasSsid) {
+    [self setSsid:other.ssid];
+  }
+  if (other.hasEncryptedPassword) {
+    [self setEncryptedPassword:other.encryptedPassword];
+  }
+  if (other.hasType) {
+    [self setType:other.type];
+  }
+  if (other.hasIsManual) {
+    [self setIsManual:other.isManual];
+  }
+  if (other.hasAuthTag) {
+    [self setAuthTag:other.authTag];
+  }
+  if (other.hasJpakeHmac) {
+    [self setJpakeHmac:other.jpakeHmac];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_WifiConnectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_WifiConnectBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setBssid:[input readString]];
+        break;
+      }
+      case 18: {
+        [self setSsid:[input readString]];
+        break;
+      }
+      case 26: {
+        [self setEncryptedPassword:[input readData]];
+        break;
+      }
+      case 32: {
+        ST_WifiConnectNetworkSecurityType value = (ST_WifiConnectNetworkSecurityType)[input readEnum];
+        if (ST_WifiConnectNetworkSecurityTypeIsValidValue(value)) {
+          [self setType:value];
+        } else {
+          [unknownFields mergeVarintField:4 value:value];
+        }
+        break;
+      }
+      case 40: {
+        [self setIsManual:[input readBool]];
+        break;
+      }
+      case 50: {
+        [self setAuthTag:[input readData]];
+        break;
+      }
+      case 58: {
+        [self setJpakeHmac:[input readData]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasBssid {
+  return result.hasBssid;
+}
+- (NSString*) bssid {
+  return result.bssid;
+}
+- (ST_WifiConnectBuilder*) setBssid:(NSString*) value {
+  result.hasBssid = YES;
+  result.bssid = value;
+  return self;
+}
+- (ST_WifiConnectBuilder*) clearBssid {
+  result.hasBssid = NO;
+  result.bssid = @"";
+  return self;
+}
+- (BOOL) hasSsid {
+  return result.hasSsid;
+}
+- (NSString*) ssid {
+  return result.ssid;
+}
+- (ST_WifiConnectBuilder*) setSsid:(NSString*) value {
+  result.hasSsid = YES;
+  result.ssid = value;
+  return self;
+}
+- (ST_WifiConnectBuilder*) clearSsid {
+  result.hasSsid = NO;
+  result.ssid = @"";
+  return self;
+}
+- (BOOL) hasEncryptedPassword {
+  return result.hasEncryptedPassword;
+}
+- (NSData*) encryptedPassword {
+  return result.encryptedPassword;
+}
+- (ST_WifiConnectBuilder*) setEncryptedPassword:(NSData*) value {
+  result.hasEncryptedPassword = YES;
+  result.encryptedPassword = value;
+  return self;
+}
+- (ST_WifiConnectBuilder*) clearEncryptedPassword {
+  result.hasEncryptedPassword = NO;
+  result.encryptedPassword = [NSData data];
+  return self;
+}
+- (BOOL) hasType {
+  return result.hasType;
+}
+- (ST_WifiConnectNetworkSecurityType) type {
+  return result.type;
+}
+- (ST_WifiConnectBuilder*) setType:(ST_WifiConnectNetworkSecurityType) value {
+  result.hasType = YES;
+  result.type = value;
+  return self;
+}
+- (ST_WifiConnectBuilder*) clearType {
+  result.hasType = NO;
+  result.type = ST_WifiConnectNetworkSecurityTypeNone;
+  return self;
+}
+- (BOOL) hasIsManual {
+  return result.hasIsManual;
+}
+- (BOOL) isManual {
+  return result.isManual;
+}
+- (ST_WifiConnectBuilder*) setIsManual:(BOOL) value {
+  result.hasIsManual = YES;
+  result.isManual = value;
+  return self;
+}
+- (ST_WifiConnectBuilder*) clearIsManual {
+  result.hasIsManual = NO;
+  result.isManual = NO;
+  return self;
+}
+- (BOOL) hasAuthTag {
+  return result.hasAuthTag;
+}
+- (NSData*) authTag {
+  return result.authTag;
+}
+- (ST_WifiConnectBuilder*) setAuthTag:(NSData*) value {
+  result.hasAuthTag = YES;
+  result.authTag = value;
+  return self;
+}
+- (ST_WifiConnectBuilder*) clearAuthTag {
+  result.hasAuthTag = NO;
+  result.authTag = [NSData data];
+  return self;
+}
+- (BOOL) hasJpakeHmac {
+  return result.hasJpakeHmac;
+}
+- (NSData*) jpakeHmac {
+  return result.jpakeHmac;
+}
+- (ST_WifiConnectBuilder*) setJpakeHmac:(NSData*) value {
+  result.hasJpakeHmac = YES;
+  result.jpakeHmac = value;
+  return self;
+}
+- (ST_WifiConnectBuilder*) clearJpakeHmac {
+  result.hasJpakeHmac = NO;
+  result.jpakeHmac = [NSData data];
+  return self;
+}
+@end
+
+@interface ST_WifiScanList ()
+@property (strong) NSString* list;
+@end
+
+@implementation ST_WifiScanList
+
+- (BOOL) hasList {
+  return !!hasList_;
+}
+- (void) setHasList:(BOOL) value_ {
+  hasList_ = !!value_;
+}
+@synthesize list;
+- (id) init {
+  if ((self = [super init])) {
+    self.list = @"";
+  }
+  return self;
+}
+static ST_WifiScanList* defaultST_WifiScanListInstance = nil;
++ (void) initialize {
+  if (self == [ST_WifiScanList class]) {
+    defaultST_WifiScanListInstance = [[ST_WifiScanList alloc] init];
+  }
+}
++ (ST_WifiScanList*) defaultInstance {
+  return defaultST_WifiScanListInstance;
+}
+- (ST_WifiScanList*) defaultInstance {
+  return defaultST_WifiScanListInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasList) {
+    [output writeString:1 value:self.list];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasList) {
+    size_ += computeStringSize(1, self.list);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_WifiScanList*) parseFromData:(NSData*) data {
+  return (ST_WifiScanList*)[[[ST_WifiScanList builder] mergeFromData:data] build];
+}
++ (ST_WifiScanList*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiScanList*)[[[ST_WifiScanList builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiScanList*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_WifiScanList*)[[[ST_WifiScanList builder] mergeFromInputStream:input] build];
+}
++ (ST_WifiScanList*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiScanList*)[[[ST_WifiScanList builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiScanList*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_WifiScanList*)[[[ST_WifiScanList builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_WifiScanList*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiScanList*)[[[ST_WifiScanList builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiScanListBuilder*) builder {
+  return [[ST_WifiScanListBuilder alloc] init];
+}
++ (ST_WifiScanListBuilder*) builderWithPrototype:(ST_WifiScanList*) prototype {
+  return [[ST_WifiScanList builder] mergeFrom:prototype];
+}
+- (ST_WifiScanListBuilder*) builder {
+  return [ST_WifiScanList builder];
+}
+- (ST_WifiScanListBuilder*) toBuilder {
+  return [ST_WifiScanList builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasList) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"list", self.list];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_WifiScanList class]]) {
+    return NO;
+  }
+  ST_WifiScanList *otherMessage = other;
+  return
+      self.hasList == otherMessage.hasList &&
+      (!self.hasList || [self.list isEqual:otherMessage.list]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasList) {
+    hashCode = hashCode * 31 + [self.list hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface ST_WifiScanListBuilder()
+@property (strong) ST_WifiScanList* result;
+@end
+
+@implementation ST_WifiScanListBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_WifiScanList alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_WifiScanListBuilder*) clear {
+  self.result = [[ST_WifiScanList alloc] init];
+  return self;
+}
+- (ST_WifiScanListBuilder*) clone {
+  return [ST_WifiScanList builderWithPrototype:result];
+}
+- (ST_WifiScanList*) defaultInstance {
+  return [ST_WifiScanList defaultInstance];
+}
+- (ST_WifiScanList*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_WifiScanList*) buildPartial {
+  ST_WifiScanList* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_WifiScanListBuilder*) mergeFrom:(ST_WifiScanList*) other {
+  if (other == [ST_WifiScanList defaultInstance]) {
+    return self;
+  }
+  if (other.hasList) {
+    [self setList:other.list];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_WifiScanListBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_WifiScanListBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setList:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasList {
+  return result.hasList;
+}
+- (NSString*) list {
+  return result.list;
+}
+- (ST_WifiScanListBuilder*) setList:(NSString*) value {
+  result.hasList = YES;
+  result.list = value;
+  return self;
+}
+- (ST_WifiScanListBuilder*) clearList {
+  result.hasList = NO;
+  result.list = @"";
+  return self;
+}
+@end
+
+@interface ST_WifiConnectStatus ()
+@property ST_WifiConnectStatusResult connectResult;
+@property (strong) NSString* debugLog;
+@end
+
+@implementation ST_WifiConnectStatus
+
+- (BOOL) hasConnectResult {
+  return !!hasConnectResult_;
+}
+- (void) setHasConnectResult:(BOOL) value_ {
+  hasConnectResult_ = !!value_;
+}
+@synthesize connectResult;
+- (BOOL) hasDebugLog {
+  return !!hasDebugLog_;
+}
+- (void) setHasDebugLog:(BOOL) value_ {
+  hasDebugLog_ = !!value_;
+}
+@synthesize debugLog;
+- (id) init {
+  if ((self = [super init])) {
+    self.connectResult = ST_WifiConnectStatusResultSuccess;
+    self.debugLog = @"";
+  }
+  return self;
+}
+static ST_WifiConnectStatus* defaultST_WifiConnectStatusInstance = nil;
++ (void) initialize {
+  if (self == [ST_WifiConnectStatus class]) {
+    defaultST_WifiConnectStatusInstance = [[ST_WifiConnectStatus alloc] init];
+  }
+}
++ (ST_WifiConnectStatus*) defaultInstance {
+  return defaultST_WifiConnectStatusInstance;
+}
+- (ST_WifiConnectStatus*) defaultInstance {
+  return defaultST_WifiConnectStatusInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasConnectResult) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasConnectResult) {
+    [output writeEnum:1 value:self.connectResult];
+  }
+  if (self.hasDebugLog) {
+    [output writeString:2 value:self.debugLog];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasConnectResult) {
+    size_ += computeEnumSize(1, self.connectResult);
+  }
+  if (self.hasDebugLog) {
+    size_ += computeStringSize(2, self.debugLog);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (ST_WifiConnectStatus*) parseFromData:(NSData*) data {
+  return (ST_WifiConnectStatus*)[[[ST_WifiConnectStatus builder] mergeFromData:data] build];
+}
++ (ST_WifiConnectStatus*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiConnectStatus*)[[[ST_WifiConnectStatus builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiConnectStatus*) parseFromInputStream:(NSInputStream*) input {
+  return (ST_WifiConnectStatus*)[[[ST_WifiConnectStatus builder] mergeFromInputStream:input] build];
+}
++ (ST_WifiConnectStatus*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiConnectStatus*)[[[ST_WifiConnectStatus builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiConnectStatus*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (ST_WifiConnectStatus*)[[[ST_WifiConnectStatus builder] mergeFromCodedInputStream:input] build];
+}
++ (ST_WifiConnectStatus*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (ST_WifiConnectStatus*)[[[ST_WifiConnectStatus builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (ST_WifiConnectStatusBuilder*) builder {
+  return [[ST_WifiConnectStatusBuilder alloc] init];
+}
++ (ST_WifiConnectStatusBuilder*) builderWithPrototype:(ST_WifiConnectStatus*) prototype {
+  return [[ST_WifiConnectStatus builder] mergeFrom:prototype];
+}
+- (ST_WifiConnectStatusBuilder*) builder {
+  return [ST_WifiConnectStatus builder];
+}
+- (ST_WifiConnectStatusBuilder*) toBuilder {
+  return [ST_WifiConnectStatus builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasConnectResult) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"connectResult", self.connectResult];
+  }
+  if (self.hasDebugLog) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"debugLog", self.debugLog];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[ST_WifiConnectStatus class]]) {
+    return NO;
+  }
+  ST_WifiConnectStatus *otherMessage = other;
+  return
+      self.hasConnectResult == otherMessage.hasConnectResult &&
+      (!self.hasConnectResult || self.connectResult == otherMessage.connectResult) &&
+      self.hasDebugLog == otherMessage.hasDebugLog &&
+      (!self.hasDebugLog || [self.debugLog isEqual:otherMessage.debugLog]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasConnectResult) {
+    hashCode = hashCode * 31 + self.connectResult;
+  }
+  if (self.hasDebugLog) {
+    hashCode = hashCode * 31 + [self.debugLog hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL ST_WifiConnectStatusResultIsValidValue(ST_WifiConnectStatusResult value) {
+  switch (value) {
+    case ST_WifiConnectStatusResultSuccess:
+    case ST_WifiConnectStatusResultBadPassword:
+    case ST_WifiConnectStatusResultNetworkNotFound:
+    case ST_WifiConnectStatusResultNoDhcp:
+    case ST_WifiConnectStatusResultNoInternet:
+    case ST_WifiConnectStatusResultNoAuth:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface ST_WifiConnectStatusBuilder()
+@property (strong) ST_WifiConnectStatus* result;
+@end
+
+@implementation ST_WifiConnectStatusBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[ST_WifiConnectStatus alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (ST_WifiConnectStatusBuilder*) clear {
+  self.result = [[ST_WifiConnectStatus alloc] init];
+  return self;
+}
+- (ST_WifiConnectStatusBuilder*) clone {
+  return [ST_WifiConnectStatus builderWithPrototype:result];
+}
+- (ST_WifiConnectStatus*) defaultInstance {
+  return [ST_WifiConnectStatus defaultInstance];
+}
+- (ST_WifiConnectStatus*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (ST_WifiConnectStatus*) buildPartial {
+  ST_WifiConnectStatus* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (ST_WifiConnectStatusBuilder*) mergeFrom:(ST_WifiConnectStatus*) other {
+  if (other == [ST_WifiConnectStatus defaultInstance]) {
+    return self;
+  }
+  if (other.hasConnectResult) {
+    [self setConnectResult:other.connectResult];
+  }
+  if (other.hasDebugLog) {
+    [self setDebugLog:other.debugLog];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (ST_WifiConnectStatusBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (ST_WifiConnectStatusBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        ST_WifiConnectStatusResult value = (ST_WifiConnectStatusResult)[input readEnum];
+        if (ST_WifiConnectStatusResultIsValidValue(value)) {
+          [self setConnectResult:value];
+        } else {
+          [unknownFields mergeVarintField:1 value:value];
+        }
+        break;
+      }
+      case 18: {
+        [self setDebugLog:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasConnectResult {
+  return result.hasConnectResult;
+}
+- (ST_WifiConnectStatusResult) connectResult {
+  return result.connectResult;
+}
+- (ST_WifiConnectStatusBuilder*) setConnectResult:(ST_WifiConnectStatusResult) value {
+  result.hasConnectResult = YES;
+  result.connectResult = value;
+  return self;
+}
+- (ST_WifiConnectStatusBuilder*) clearConnectResult {
+  result.hasConnectResult = NO;
+  result.connectResult = ST_WifiConnectStatusResultSuccess;
+  return self;
+}
+- (BOOL) hasDebugLog {
+  return result.hasDebugLog;
+}
+- (NSString*) debugLog {
+  return result.debugLog;
+}
+- (ST_WifiConnectStatusBuilder*) setDebugLog:(NSString*) value {
+  result.hasDebugLog = YES;
+  result.debugLog = value;
+  return self;
+}
+- (ST_WifiConnectStatusBuilder*) clearDebugLog {
+  result.hasDebugLog = NO;
+  result.debugLog = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Software_profile.pb.h b/src/gen_proto/Software_profile.pb.h
new file mode 100644
index 0000000..c25ddcd
--- /dev/null
+++ b/src/gen_proto/Software_profile.pb.h
@@ -0,0 +1,96 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+@class SoftwareProfile;
+@class SoftwareProfileBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+
+@interface SoftwareProfileRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface SoftwareProfile : PBGeneratedMessage {
+@private
+  BOOL hasUpdateTime_:1;
+  BOOL hasVersion_:1;
+  BOOL hasDescription_:1;
+  SInt64 updateTime;
+  NSString* version;
+  NSString* description;
+}
+- (BOOL) hasVersion;
+- (BOOL) hasUpdateTime;
+- (BOOL) hasDescription;
+@property (readonly, strong) NSString* version;
+@property (readonly) SInt64 updateTime;
+@property (readonly, strong) NSString* description;
+
++ (SoftwareProfile*) defaultInstance;
+- (SoftwareProfile*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (SoftwareProfileBuilder*) builder;
++ (SoftwareProfileBuilder*) builder;
++ (SoftwareProfileBuilder*) builderWithPrototype:(SoftwareProfile*) prototype;
+- (SoftwareProfileBuilder*) toBuilder;
+
++ (SoftwareProfile*) parseFromData:(NSData*) data;
++ (SoftwareProfile*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (SoftwareProfile*) parseFromInputStream:(NSInputStream*) input;
++ (SoftwareProfile*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (SoftwareProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (SoftwareProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface SoftwareProfileBuilder : PBGeneratedMessageBuilder {
+@private
+  SoftwareProfile* result;
+}
+
+- (SoftwareProfile*) defaultInstance;
+
+- (SoftwareProfileBuilder*) clear;
+- (SoftwareProfileBuilder*) clone;
+
+- (SoftwareProfile*) build;
+- (SoftwareProfile*) buildPartial;
+
+- (SoftwareProfileBuilder*) mergeFrom:(SoftwareProfile*) other;
+- (SoftwareProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (SoftwareProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasVersion;
+- (NSString*) version;
+- (SoftwareProfileBuilder*) setVersion:(NSString*) value;
+- (SoftwareProfileBuilder*) clearVersion;
+
+- (BOOL) hasUpdateTime;
+- (SInt64) updateTime;
+- (SoftwareProfileBuilder*) setUpdateTime:(SInt64) value;
+- (SoftwareProfileBuilder*) clearUpdateTime;
+
+- (BOOL) hasDescription;
+- (NSString*) description;
+- (SoftwareProfileBuilder*) setDescription:(NSString*) value;
+- (SoftwareProfileBuilder*) clearDescription;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Software_profile.pb.m b/src/gen_proto/Software_profile.pb.m
new file mode 100644
index 0000000..25d9a4a
--- /dev/null
+++ b/src/gen_proto/Software_profile.pb.m
@@ -0,0 +1,316 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Software_profile.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation SoftwareProfileRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [SoftwareProfileRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface SoftwareProfile ()
+@property (strong) NSString* version;
+@property SInt64 updateTime;
+@property (strong) NSString* description;
+@end
+
+@implementation SoftwareProfile
+
+- (BOOL) hasVersion {
+  return !!hasVersion_;
+}
+- (void) setHasVersion:(BOOL) value_ {
+  hasVersion_ = !!value_;
+}
+@synthesize version;
+- (BOOL) hasUpdateTime {
+  return !!hasUpdateTime_;
+}
+- (void) setHasUpdateTime:(BOOL) value_ {
+  hasUpdateTime_ = !!value_;
+}
+@synthesize updateTime;
+- (BOOL) hasDescription {
+  return !!hasDescription_;
+}
+- (void) setHasDescription:(BOOL) value_ {
+  hasDescription_ = !!value_;
+}
+@synthesize description;
+- (id) init {
+  if ((self = [super init])) {
+    self.version = @"";
+    self.updateTime = 0L;
+    self.description = @"";
+  }
+  return self;
+}
+static SoftwareProfile* defaultSoftwareProfileInstance = nil;
++ (void) initialize {
+  if (self == [SoftwareProfile class]) {
+    defaultSoftwareProfileInstance = [[SoftwareProfile alloc] init];
+  }
+}
++ (SoftwareProfile*) defaultInstance {
+  return defaultSoftwareProfileInstance;
+}
+- (SoftwareProfile*) defaultInstance {
+  return defaultSoftwareProfileInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasVersion) {
+    [output writeString:1 value:self.version];
+  }
+  if (self.hasUpdateTime) {
+    [output writeInt64:2 value:self.updateTime];
+  }
+  if (self.hasDescription) {
+    [output writeString:3 value:self.description];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasVersion) {
+    size_ += computeStringSize(1, self.version);
+  }
+  if (self.hasUpdateTime) {
+    size_ += computeInt64Size(2, self.updateTime);
+  }
+  if (self.hasDescription) {
+    size_ += computeStringSize(3, self.description);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (SoftwareProfile*) parseFromData:(NSData*) data {
+  return (SoftwareProfile*)[[[SoftwareProfile builder] mergeFromData:data] build];
+}
++ (SoftwareProfile*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (SoftwareProfile*)[[[SoftwareProfile builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (SoftwareProfile*) parseFromInputStream:(NSInputStream*) input {
+  return (SoftwareProfile*)[[[SoftwareProfile builder] mergeFromInputStream:input] build];
+}
++ (SoftwareProfile*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (SoftwareProfile*)[[[SoftwareProfile builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (SoftwareProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (SoftwareProfile*)[[[SoftwareProfile builder] mergeFromCodedInputStream:input] build];
+}
++ (SoftwareProfile*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (SoftwareProfile*)[[[SoftwareProfile builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (SoftwareProfileBuilder*) builder {
+  return [[SoftwareProfileBuilder alloc] init];
+}
++ (SoftwareProfileBuilder*) builderWithPrototype:(SoftwareProfile*) prototype {
+  return [[SoftwareProfile builder] mergeFrom:prototype];
+}
+- (SoftwareProfileBuilder*) builder {
+  return [SoftwareProfile builder];
+}
+- (SoftwareProfileBuilder*) toBuilder {
+  return [SoftwareProfile builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasVersion) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"version", self.version];
+  }
+  if (self.hasUpdateTime) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"updateTime", [NSNumber numberWithLongLong:self.updateTime]];
+  }
+  if (self.hasDescription) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"description", self.description];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[SoftwareProfile class]]) {
+    return NO;
+  }
+  SoftwareProfile *otherMessage = other;
+  return
+      self.hasVersion == otherMessage.hasVersion &&
+      (!self.hasVersion || [self.version isEqual:otherMessage.version]) &&
+      self.hasUpdateTime == otherMessage.hasUpdateTime &&
+      (!self.hasUpdateTime || self.updateTime == otherMessage.updateTime) &&
+      self.hasDescription == otherMessage.hasDescription &&
+      (!self.hasDescription || [self.description isEqual:otherMessage.description]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasVersion) {
+    hashCode = hashCode * 31 + [self.version hash];
+  }
+  if (self.hasUpdateTime) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.updateTime] hash];
+  }
+  if (self.hasDescription) {
+    hashCode = hashCode * 31 + [self.description hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface SoftwareProfileBuilder()
+@property (strong) SoftwareProfile* result;
+@end
+
+@implementation SoftwareProfileBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[SoftwareProfile alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (SoftwareProfileBuilder*) clear {
+  self.result = [[SoftwareProfile alloc] init];
+  return self;
+}
+- (SoftwareProfileBuilder*) clone {
+  return [SoftwareProfile builderWithPrototype:result];
+}
+- (SoftwareProfile*) defaultInstance {
+  return [SoftwareProfile defaultInstance];
+}
+- (SoftwareProfile*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (SoftwareProfile*) buildPartial {
+  SoftwareProfile* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (SoftwareProfileBuilder*) mergeFrom:(SoftwareProfile*) other {
+  if (other == [SoftwareProfile defaultInstance]) {
+    return self;
+  }
+  if (other.hasVersion) {
+    [self setVersion:other.version];
+  }
+  if (other.hasUpdateTime) {
+    [self setUpdateTime:other.updateTime];
+  }
+  if (other.hasDescription) {
+    [self setDescription:other.description];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (SoftwareProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (SoftwareProfileBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setVersion:[input readString]];
+        break;
+      }
+      case 16: {
+        [self setUpdateTime:[input readInt64]];
+        break;
+      }
+      case 26: {
+        [self setDescription:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasVersion {
+  return result.hasVersion;
+}
+- (NSString*) version {
+  return result.version;
+}
+- (SoftwareProfileBuilder*) setVersion:(NSString*) value {
+  result.hasVersion = YES;
+  result.version = value;
+  return self;
+}
+- (SoftwareProfileBuilder*) clearVersion {
+  result.hasVersion = NO;
+  result.version = @"";
+  return self;
+}
+- (BOOL) hasUpdateTime {
+  return result.hasUpdateTime;
+}
+- (SInt64) updateTime {
+  return result.updateTime;
+}
+- (SoftwareProfileBuilder*) setUpdateTime:(SInt64) value {
+  result.hasUpdateTime = YES;
+  result.updateTime = value;
+  return self;
+}
+- (SoftwareProfileBuilder*) clearUpdateTime {
+  result.hasUpdateTime = NO;
+  result.updateTime = 0L;
+  return self;
+}
+- (BOOL) hasDescription {
+  return result.hasDescription;
+}
+- (NSString*) description {
+  return result.description;
+}
+- (SoftwareProfileBuilder*) setDescription:(NSString*) value {
+  result.hasDescription = YES;
+  result.description = value;
+  return self;
+}
+- (SoftwareProfileBuilder*) clearDescription {
+  result.hasDescription = NO;
+  result.description = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Weave_operation.pb.h b/src/gen_proto/Weave_operation.pb.h
new file mode 100644
index 0000000..8ac5c93
--- /dev/null
+++ b/src/gen_proto/Weave_operation.pb.h
@@ -0,0 +1,64 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+// @@protoc_insertion_point(imports)
+
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  WeaveOperationNone = 0,
+  WeaveOperationConnect = 1,
+  WeaveOperationRendezvous = 2,
+  WeaveOperationReconnect = 3,
+  WeaveOperationIdentify = 4,
+  WeaveOperationScanNetworks = 5,
+  WeaveOperationGetNetworks = 6,
+  WeaveOperationAddNetwork = 7,
+  WeaveOperationUpdateNetwork = 8,
+  WeaveOperationRemoveNetwork = 9,
+  WeaveOperationEnableNetwork = 10,
+  WeaveOperationDisableNetwork = 11,
+  WeaveOperationTestNetwork = 12,
+  WeaveOperationGetRendezvousMode = 13,
+  WeaveOperationSetRendezvousMode = 14,
+  WeaveOperationGetLastNetworkProvisioningResult = 15,
+  WeaveOperationRegisterServicePairAccount = 16,
+  WeaveOperationUnregisterService = 17,
+  WeaveOperationCreateFabric = 18,
+  WeaveOperationLeaveFabric = 19,
+  WeaveOperationGetFabricConfig = 20,
+  WeaveOperationJoinExistingFabric = 21,
+  WeaveOperationArmFailsafe = 22,
+  WeaveOperationDisarmFailsafe = 23,
+  WeaveOperationResetConfig = 24,
+  WeaveOperationPing = 25,
+  WeaveOperationEnableConnectionMonitor = 26,
+  WeaveOperationDisableConnectionMonitor = 27,
+  WeaveOperationConnectBle = 28,
+  WeaveOperationHush = 29,
+  WeaveOperationStartSystemTest = 30,
+  WeaveOperationStopSystemTest = 31,
+} WeaveOperation;
+
+BOOL WeaveOperationIsValidValue(WeaveOperation value);
+
+
+@interface WeaveOperationRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Weave_operation.pb.m b/src/gen_proto/Weave_operation.pb.m
new file mode 100644
index 0000000..d3d54cf
--- /dev/null
+++ b/src/gen_proto/Weave_operation.pb.m
@@ -0,0 +1,63 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Weave_operation.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation WeaveOperationRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [WeaveOperationRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+BOOL WeaveOperationIsValidValue(WeaveOperation value) {
+  switch (value) {
+    case WeaveOperationNone:
+    case WeaveOperationConnect:
+    case WeaveOperationRendezvous:
+    case WeaveOperationReconnect:
+    case WeaveOperationIdentify:
+    case WeaveOperationScanNetworks:
+    case WeaveOperationGetNetworks:
+    case WeaveOperationAddNetwork:
+    case WeaveOperationUpdateNetwork:
+    case WeaveOperationRemoveNetwork:
+    case WeaveOperationEnableNetwork:
+    case WeaveOperationDisableNetwork:
+    case WeaveOperationTestNetwork:
+    case WeaveOperationGetRendezvousMode:
+    case WeaveOperationSetRendezvousMode:
+    case WeaveOperationGetLastNetworkProvisioningResult:
+    case WeaveOperationRegisterServicePairAccount:
+    case WeaveOperationUnregisterService:
+    case WeaveOperationCreateFabric:
+    case WeaveOperationLeaveFabric:
+    case WeaveOperationGetFabricConfig:
+    case WeaveOperationJoinExistingFabric:
+    case WeaveOperationArmFailsafe:
+    case WeaveOperationDisarmFailsafe:
+    case WeaveOperationResetConfig:
+    case WeaveOperationPing:
+    case WeaveOperationEnableConnectionMonitor:
+    case WeaveOperationDisableConnectionMonitor:
+    case WeaveOperationConnectBle:
+    case WeaveOperationHush:
+    case WeaveOperationStartSystemTest:
+    case WeaveOperationStopSystemTest:
+      return YES;
+    default:
+      return NO;
+  }
+}
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Weave_pairing_session_log.pb.h b/src/gen_proto/Weave_pairing_session_log.pb.h
new file mode 100644
index 0000000..b8a0707
--- /dev/null
+++ b/src/gen_proto/Weave_pairing_session_log.pb.h
@@ -0,0 +1,237 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "ProtocolBuffers.h"
+
+#import "Environment.pb.h"
+#import "Event.pb.h"
+#import "Identification_profile.pb.h"
+#import "Software_profile.pb.h"
+#import "Account_info.pb.h"
+#import "Fabric_info.pb.h"
+// @@protoc_insertion_point(imports)
+
+@class AccountInfo;
+@class AccountInfoBuilder;
+@class Environment;
+@class EnvironmentBuilder;
+@class Event;
+@class EventBuilder;
+@class FabricInfo;
+@class FabricInfoBuilder;
+@class IdentificationProfile;
+@class IdentificationProfileBuilder;
+@class Pair;
+@class PairBuilder;
+@class SoftwareProfile;
+@class SoftwareProfileBuilder;
+@class WeavePairingSessionLog;
+@class WeavePairingSessionLogBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  WeavePairingSessionLogStatusUnknown = 0,
+  WeavePairingSessionLogStatusSuccess = 1,
+  WeavePairingSessionLogStatusFailure = 2,
+} WeavePairingSessionLogStatus;
+
+BOOL WeavePairingSessionLogStatusIsValidValue(WeavePairingSessionLogStatus value);
+
+
+@interface WeavePairingSessionLogRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface WeavePairingSessionLog : PBGeneratedMessage {
+@private
+  BOOL hasSessionId_:1;
+  BOOL hasSessionStartTimestampIso8601_:1;
+  BOOL hasSessionEndTimestampIso8601_:1;
+  BOOL hasEnvironment_:1;
+  BOOL hasJoiningDeviceIdentification_:1;
+  BOOL hasJoiningDeviceSoftware_:1;
+  BOOL hasAssistingDeviceIdentification_:1;
+  BOOL hasAssistingDeviceSoftware_:1;
+  BOOL hasAccountInfo_:1;
+  BOOL hasFabricInfo_:1;
+  BOOL hasSessionStatus_:1;
+  BOOL hasSessionStartTimestampMillis_:1;
+  BOOL hasSessionEndTimestampMillis_:1;
+  NSString* sessionId;
+  NSString* sessionStartTimestampIso8601;
+  NSString* sessionEndTimestampIso8601;
+  Environment* environment;
+  IdentificationProfile* joiningDeviceIdentification;
+  SoftwareProfile* joiningDeviceSoftware;
+  IdentificationProfile* assistingDeviceIdentification;
+  SoftwareProfile* assistingDeviceSoftware;
+  AccountInfo* accountInfo;
+  FabricInfo* fabricInfo;
+  WeavePairingSessionLogStatus sessionStatus;
+  SInt64 sessionStartTimestampMillis;
+  SInt64 sessionEndTimestampMillis;
+  NSMutableArray * eventsArray;
+}
+- (BOOL) hasSessionStartTimestampMillis;
+- (BOOL) hasSessionEndTimestampMillis;
+- (BOOL) hasSessionStatus;
+- (BOOL) hasSessionId;
+- (BOOL) hasEnvironment;
+- (BOOL) hasJoiningDeviceIdentification;
+- (BOOL) hasJoiningDeviceSoftware;
+- (BOOL) hasAssistingDeviceIdentification;
+- (BOOL) hasAssistingDeviceSoftware;
+- (BOOL) hasAccountInfo;
+- (BOOL) hasFabricInfo;
+- (BOOL) hasSessionStartTimestampIso8601;
+- (BOOL) hasSessionEndTimestampIso8601;
+@property (readonly) SInt64 sessionStartTimestampMillis;
+@property (readonly) SInt64 sessionEndTimestampMillis;
+@property (readonly) WeavePairingSessionLogStatus sessionStatus;
+@property (readonly, strong) NSString* sessionId;
+@property (readonly, strong) NSArray * events;
+@property (readonly, strong) Environment* environment;
+@property (readonly, strong) IdentificationProfile* joiningDeviceIdentification;
+@property (readonly, strong) SoftwareProfile* joiningDeviceSoftware;
+@property (readonly, strong) IdentificationProfile* assistingDeviceIdentification;
+@property (readonly, strong) SoftwareProfile* assistingDeviceSoftware;
+@property (readonly, strong) AccountInfo* accountInfo;
+@property (readonly, strong) FabricInfo* fabricInfo;
+@property (readonly, strong) NSString* sessionStartTimestampIso8601;
+@property (readonly, strong) NSString* sessionEndTimestampIso8601;
+- (Event*)eventsAtIndex:(NSUInteger)index;
+
++ (WeavePairingSessionLog*) defaultInstance;
+- (WeavePairingSessionLog*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (WeavePairingSessionLogBuilder*) builder;
++ (WeavePairingSessionLogBuilder*) builder;
++ (WeavePairingSessionLogBuilder*) builderWithPrototype:(WeavePairingSessionLog*) prototype;
+- (WeavePairingSessionLogBuilder*) toBuilder;
+
++ (WeavePairingSessionLog*) parseFromData:(NSData*) data;
++ (WeavePairingSessionLog*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (WeavePairingSessionLog*) parseFromInputStream:(NSInputStream*) input;
++ (WeavePairingSessionLog*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (WeavePairingSessionLog*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (WeavePairingSessionLog*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface WeavePairingSessionLogBuilder : PBGeneratedMessageBuilder {
+@private
+  WeavePairingSessionLog* result;
+}
+
+- (WeavePairingSessionLog*) defaultInstance;
+
+- (WeavePairingSessionLogBuilder*) clear;
+- (WeavePairingSessionLogBuilder*) clone;
+
+- (WeavePairingSessionLog*) build;
+- (WeavePairingSessionLog*) buildPartial;
+
+- (WeavePairingSessionLogBuilder*) mergeFrom:(WeavePairingSessionLog*) other;
+- (WeavePairingSessionLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (WeavePairingSessionLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasSessionStartTimestampMillis;
+- (SInt64) sessionStartTimestampMillis;
+- (WeavePairingSessionLogBuilder*) setSessionStartTimestampMillis:(SInt64) value;
+- (WeavePairingSessionLogBuilder*) clearSessionStartTimestampMillis;
+
+- (BOOL) hasSessionEndTimestampMillis;
+- (SInt64) sessionEndTimestampMillis;
+- (WeavePairingSessionLogBuilder*) setSessionEndTimestampMillis:(SInt64) value;
+- (WeavePairingSessionLogBuilder*) clearSessionEndTimestampMillis;
+
+- (BOOL) hasSessionStatus;
+- (WeavePairingSessionLogStatus) sessionStatus;
+- (WeavePairingSessionLogBuilder*) setSessionStatus:(WeavePairingSessionLogStatus) value;
+- (WeavePairingSessionLogBuilder*) clearSessionStatus;
+
+- (BOOL) hasSessionId;
+- (NSString*) sessionId;
+- (WeavePairingSessionLogBuilder*) setSessionId:(NSString*) value;
+- (WeavePairingSessionLogBuilder*) clearSessionId;
+
+- (NSMutableArray *)events;
+- (Event*)eventsAtIndex:(NSUInteger)index;
+- (WeavePairingSessionLogBuilder *)addEvents:(Event*)value;
+- (WeavePairingSessionLogBuilder *)setEventsArray:(NSArray *)array;
+- (WeavePairingSessionLogBuilder *)clearEvents;
+
+- (BOOL) hasEnvironment;
+- (Environment*) environment;
+- (WeavePairingSessionLogBuilder*) setEnvironment:(Environment*) value;
+- (WeavePairingSessionLogBuilder*) setEnvironmentBuilder:(EnvironmentBuilder*) builderForValue;
+- (WeavePairingSessionLogBuilder*) mergeEnvironment:(Environment*) value;
+- (WeavePairingSessionLogBuilder*) clearEnvironment;
+
+- (BOOL) hasJoiningDeviceIdentification;
+- (IdentificationProfile*) joiningDeviceIdentification;
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceIdentification:(IdentificationProfile*) value;
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceIdentificationBuilder:(IdentificationProfileBuilder*) builderForValue;
+- (WeavePairingSessionLogBuilder*) mergeJoiningDeviceIdentification:(IdentificationProfile*) value;
+- (WeavePairingSessionLogBuilder*) clearJoiningDeviceIdentification;
+
+- (BOOL) hasJoiningDeviceSoftware;
+- (SoftwareProfile*) joiningDeviceSoftware;
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceSoftware:(SoftwareProfile*) value;
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceSoftwareBuilder:(SoftwareProfileBuilder*) builderForValue;
+- (WeavePairingSessionLogBuilder*) mergeJoiningDeviceSoftware:(SoftwareProfile*) value;
+- (WeavePairingSessionLogBuilder*) clearJoiningDeviceSoftware;
+
+- (BOOL) hasAssistingDeviceIdentification;
+- (IdentificationProfile*) assistingDeviceIdentification;
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceIdentification:(IdentificationProfile*) value;
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceIdentificationBuilder:(IdentificationProfileBuilder*) builderForValue;
+- (WeavePairingSessionLogBuilder*) mergeAssistingDeviceIdentification:(IdentificationProfile*) value;
+- (WeavePairingSessionLogBuilder*) clearAssistingDeviceIdentification;
+
+- (BOOL) hasAssistingDeviceSoftware;
+- (SoftwareProfile*) assistingDeviceSoftware;
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceSoftware:(SoftwareProfile*) value;
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceSoftwareBuilder:(SoftwareProfileBuilder*) builderForValue;
+- (WeavePairingSessionLogBuilder*) mergeAssistingDeviceSoftware:(SoftwareProfile*) value;
+- (WeavePairingSessionLogBuilder*) clearAssistingDeviceSoftware;
+
+- (BOOL) hasAccountInfo;
+- (AccountInfo*) accountInfo;
+- (WeavePairingSessionLogBuilder*) setAccountInfo:(AccountInfo*) value;
+- (WeavePairingSessionLogBuilder*) setAccountInfoBuilder:(AccountInfoBuilder*) builderForValue;
+- (WeavePairingSessionLogBuilder*) mergeAccountInfo:(AccountInfo*) value;
+- (WeavePairingSessionLogBuilder*) clearAccountInfo;
+
+- (BOOL) hasFabricInfo;
+- (FabricInfo*) fabricInfo;
+- (WeavePairingSessionLogBuilder*) setFabricInfo:(FabricInfo*) value;
+- (WeavePairingSessionLogBuilder*) setFabricInfoBuilder:(FabricInfoBuilder*) builderForValue;
+- (WeavePairingSessionLogBuilder*) mergeFabricInfo:(FabricInfo*) value;
+- (WeavePairingSessionLogBuilder*) clearFabricInfo;
+
+- (BOOL) hasSessionStartTimestampIso8601;
+- (NSString*) sessionStartTimestampIso8601;
+- (WeavePairingSessionLogBuilder*) setSessionStartTimestampIso8601:(NSString*) value;
+- (WeavePairingSessionLogBuilder*) clearSessionStartTimestampIso8601;
+
+- (BOOL) hasSessionEndTimestampIso8601;
+- (NSString*) sessionEndTimestampIso8601;
+- (WeavePairingSessionLogBuilder*) setSessionEndTimestampIso8601:(NSString*) value;
+- (WeavePairingSessionLogBuilder*) clearSessionEndTimestampIso8601;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/gen_proto/Weave_pairing_session_log.pb.m b/src/gen_proto/Weave_pairing_session_log.pb.m
new file mode 100644
index 0000000..316fb5f
--- /dev/null
+++ b/src/gen_proto/Weave_pairing_session_log.pb.m
@@ -0,0 +1,1010 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+#import "Weave_pairing_session_log.pb.h"
+// @@protoc_insertion_point(imports)
+
+@implementation WeavePairingSessionLogRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [WeavePairingSessionLogRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    [EnvironmentRoot registerAllExtensions:registry];
+    [EventRoot registerAllExtensions:registry];
+    [IdentificationProfileRoot registerAllExtensions:registry];
+    [SoftwareProfileRoot registerAllExtensions:registry];
+    [AccountInfoRoot registerAllExtensions:registry];
+    [FabricInfoRoot registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface WeavePairingSessionLog ()
+@property SInt64 sessionStartTimestampMillis;
+@property SInt64 sessionEndTimestampMillis;
+@property WeavePairingSessionLogStatus sessionStatus;
+@property (strong) NSString* sessionId;
+@property (strong) NSMutableArray * eventsArray;
+@property (strong) Environment* environment;
+@property (strong) IdentificationProfile* joiningDeviceIdentification;
+@property (strong) SoftwareProfile* joiningDeviceSoftware;
+@property (strong) IdentificationProfile* assistingDeviceIdentification;
+@property (strong) SoftwareProfile* assistingDeviceSoftware;
+@property (strong) AccountInfo* accountInfo;
+@property (strong) FabricInfo* fabricInfo;
+@property (strong) NSString* sessionStartTimestampIso8601;
+@property (strong) NSString* sessionEndTimestampIso8601;
+@end
+
+@implementation WeavePairingSessionLog
+
+- (BOOL) hasSessionStartTimestampMillis {
+  return !!hasSessionStartTimestampMillis_;
+}
+- (void) setHasSessionStartTimestampMillis:(BOOL) value_ {
+  hasSessionStartTimestampMillis_ = !!value_;
+}
+@synthesize sessionStartTimestampMillis;
+- (BOOL) hasSessionEndTimestampMillis {
+  return !!hasSessionEndTimestampMillis_;
+}
+- (void) setHasSessionEndTimestampMillis:(BOOL) value_ {
+  hasSessionEndTimestampMillis_ = !!value_;
+}
+@synthesize sessionEndTimestampMillis;
+- (BOOL) hasSessionStatus {
+  return !!hasSessionStatus_;
+}
+- (void) setHasSessionStatus:(BOOL) value_ {
+  hasSessionStatus_ = !!value_;
+}
+@synthesize sessionStatus;
+- (BOOL) hasSessionId {
+  return !!hasSessionId_;
+}
+- (void) setHasSessionId:(BOOL) value_ {
+  hasSessionId_ = !!value_;
+}
+@synthesize sessionId;
+@synthesize eventsArray;
+@dynamic events;
+- (BOOL) hasEnvironment {
+  return !!hasEnvironment_;
+}
+- (void) setHasEnvironment:(BOOL) value_ {
+  hasEnvironment_ = !!value_;
+}
+@synthesize environment;
+- (BOOL) hasJoiningDeviceIdentification {
+  return !!hasJoiningDeviceIdentification_;
+}
+- (void) setHasJoiningDeviceIdentification:(BOOL) value_ {
+  hasJoiningDeviceIdentification_ = !!value_;
+}
+@synthesize joiningDeviceIdentification;
+- (BOOL) hasJoiningDeviceSoftware {
+  return !!hasJoiningDeviceSoftware_;
+}
+- (void) setHasJoiningDeviceSoftware:(BOOL) value_ {
+  hasJoiningDeviceSoftware_ = !!value_;
+}
+@synthesize joiningDeviceSoftware;
+- (BOOL) hasAssistingDeviceIdentification {
+  return !!hasAssistingDeviceIdentification_;
+}
+- (void) setHasAssistingDeviceIdentification:(BOOL) value_ {
+  hasAssistingDeviceIdentification_ = !!value_;
+}
+@synthesize assistingDeviceIdentification;
+- (BOOL) hasAssistingDeviceSoftware {
+  return !!hasAssistingDeviceSoftware_;
+}
+- (void) setHasAssistingDeviceSoftware:(BOOL) value_ {
+  hasAssistingDeviceSoftware_ = !!value_;
+}
+@synthesize assistingDeviceSoftware;
+- (BOOL) hasAccountInfo {
+  return !!hasAccountInfo_;
+}
+- (void) setHasAccountInfo:(BOOL) value_ {
+  hasAccountInfo_ = !!value_;
+}
+@synthesize accountInfo;
+- (BOOL) hasFabricInfo {
+  return !!hasFabricInfo_;
+}
+- (void) setHasFabricInfo:(BOOL) value_ {
+  hasFabricInfo_ = !!value_;
+}
+@synthesize fabricInfo;
+- (BOOL) hasSessionStartTimestampIso8601 {
+  return !!hasSessionStartTimestampIso8601_;
+}
+- (void) setHasSessionStartTimestampIso8601:(BOOL) value_ {
+  hasSessionStartTimestampIso8601_ = !!value_;
+}
+@synthesize sessionStartTimestampIso8601;
+- (BOOL) hasSessionEndTimestampIso8601 {
+  return !!hasSessionEndTimestampIso8601_;
+}
+- (void) setHasSessionEndTimestampIso8601:(BOOL) value_ {
+  hasSessionEndTimestampIso8601_ = !!value_;
+}
+@synthesize sessionEndTimestampIso8601;
+- (id) init {
+  if ((self = [super init])) {
+    self.sessionStartTimestampMillis = 0L;
+    self.sessionEndTimestampMillis = 0L;
+    self.sessionStatus = WeavePairingSessionLogStatusUnknown;
+    self.sessionId = @"";
+    self.environment = [Environment defaultInstance];
+    self.joiningDeviceIdentification = [IdentificationProfile defaultInstance];
+    self.joiningDeviceSoftware = [SoftwareProfile defaultInstance];
+    self.assistingDeviceIdentification = [IdentificationProfile defaultInstance];
+    self.assistingDeviceSoftware = [SoftwareProfile defaultInstance];
+    self.accountInfo = [AccountInfo defaultInstance];
+    self.fabricInfo = [FabricInfo defaultInstance];
+    self.sessionStartTimestampIso8601 = @"";
+    self.sessionEndTimestampIso8601 = @"";
+  }
+  return self;
+}
+static WeavePairingSessionLog* defaultWeavePairingSessionLogInstance = nil;
++ (void) initialize {
+  if (self == [WeavePairingSessionLog class]) {
+    defaultWeavePairingSessionLogInstance = [[WeavePairingSessionLog alloc] init];
+  }
+}
++ (WeavePairingSessionLog*) defaultInstance {
+  return defaultWeavePairingSessionLogInstance;
+}
+- (WeavePairingSessionLog*) defaultInstance {
+  return defaultWeavePairingSessionLogInstance;
+}
+- (NSArray *)events {
+  return eventsArray;
+}
+- (Event*)eventsAtIndex:(NSUInteger)index {
+  return [eventsArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasSessionStartTimestampMillis) {
+    [output writeSInt64:1 value:self.sessionStartTimestampMillis];
+  }
+  if (self.hasSessionEndTimestampMillis) {
+    [output writeSInt64:2 value:self.sessionEndTimestampMillis];
+  }
+  if (self.hasSessionStatus) {
+    [output writeEnum:3 value:self.sessionStatus];
+  }
+  if (self.hasSessionId) {
+    [output writeString:4 value:self.sessionId];
+  }
+  [self.eventsArray enumerateObjectsUsingBlock:^(Event *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:5 value:element];
+  }];
+  if (self.hasEnvironment) {
+    [output writeMessage:6 value:self.environment];
+  }
+  if (self.hasJoiningDeviceIdentification) {
+    [output writeMessage:7 value:self.joiningDeviceIdentification];
+  }
+  if (self.hasJoiningDeviceSoftware) {
+    [output writeMessage:8 value:self.joiningDeviceSoftware];
+  }
+  if (self.hasAssistingDeviceIdentification) {
+    [output writeMessage:9 value:self.assistingDeviceIdentification];
+  }
+  if (self.hasAssistingDeviceSoftware) {
+    [output writeMessage:10 value:self.assistingDeviceSoftware];
+  }
+  if (self.hasAccountInfo) {
+    [output writeMessage:11 value:self.accountInfo];
+  }
+  if (self.hasFabricInfo) {
+    [output writeMessage:12 value:self.fabricInfo];
+  }
+  if (self.hasSessionStartTimestampIso8601) {
+    [output writeString:13 value:self.sessionStartTimestampIso8601];
+  }
+  if (self.hasSessionEndTimestampIso8601) {
+    [output writeString:14 value:self.sessionEndTimestampIso8601];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasSessionStartTimestampMillis) {
+    size_ += computeSInt64Size(1, self.sessionStartTimestampMillis);
+  }
+  if (self.hasSessionEndTimestampMillis) {
+    size_ += computeSInt64Size(2, self.sessionEndTimestampMillis);
+  }
+  if (self.hasSessionStatus) {
+    size_ += computeEnumSize(3, self.sessionStatus);
+  }
+  if (self.hasSessionId) {
+    size_ += computeStringSize(4, self.sessionId);
+  }
+  [self.eventsArray enumerateObjectsUsingBlock:^(Event *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(5, element);
+  }];
+  if (self.hasEnvironment) {
+    size_ += computeMessageSize(6, self.environment);
+  }
+  if (self.hasJoiningDeviceIdentification) {
+    size_ += computeMessageSize(7, self.joiningDeviceIdentification);
+  }
+  if (self.hasJoiningDeviceSoftware) {
+    size_ += computeMessageSize(8, self.joiningDeviceSoftware);
+  }
+  if (self.hasAssistingDeviceIdentification) {
+    size_ += computeMessageSize(9, self.assistingDeviceIdentification);
+  }
+  if (self.hasAssistingDeviceSoftware) {
+    size_ += computeMessageSize(10, self.assistingDeviceSoftware);
+  }
+  if (self.hasAccountInfo) {
+    size_ += computeMessageSize(11, self.accountInfo);
+  }
+  if (self.hasFabricInfo) {
+    size_ += computeMessageSize(12, self.fabricInfo);
+  }
+  if (self.hasSessionStartTimestampIso8601) {
+    size_ += computeStringSize(13, self.sessionStartTimestampIso8601);
+  }
+  if (self.hasSessionEndTimestampIso8601) {
+    size_ += computeStringSize(14, self.sessionEndTimestampIso8601);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (WeavePairingSessionLog*) parseFromData:(NSData*) data {
+  return (WeavePairingSessionLog*)[[[WeavePairingSessionLog builder] mergeFromData:data] build];
+}
++ (WeavePairingSessionLog*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (WeavePairingSessionLog*)[[[WeavePairingSessionLog builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (WeavePairingSessionLog*) parseFromInputStream:(NSInputStream*) input {
+  return (WeavePairingSessionLog*)[[[WeavePairingSessionLog builder] mergeFromInputStream:input] build];
+}
++ (WeavePairingSessionLog*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (WeavePairingSessionLog*)[[[WeavePairingSessionLog builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (WeavePairingSessionLog*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (WeavePairingSessionLog*)[[[WeavePairingSessionLog builder] mergeFromCodedInputStream:input] build];
+}
++ (WeavePairingSessionLog*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (WeavePairingSessionLog*)[[[WeavePairingSessionLog builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (WeavePairingSessionLogBuilder*) builder {
+  return [[WeavePairingSessionLogBuilder alloc] init];
+}
++ (WeavePairingSessionLogBuilder*) builderWithPrototype:(WeavePairingSessionLog*) prototype {
+  return [[WeavePairingSessionLog builder] mergeFrom:prototype];
+}
+- (WeavePairingSessionLogBuilder*) builder {
+  return [WeavePairingSessionLog builder];
+}
+- (WeavePairingSessionLogBuilder*) toBuilder {
+  return [WeavePairingSessionLog builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasSessionStartTimestampMillis) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionStartTimestampMillis", [NSNumber numberWithLongLong:self.sessionStartTimestampMillis]];
+  }
+  if (self.hasSessionEndTimestampMillis) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionEndTimestampMillis", [NSNumber numberWithLongLong:self.sessionEndTimestampMillis]];
+  }
+  if (self.hasSessionStatus) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"sessionStatus", self.sessionStatus];
+  }
+  if (self.hasSessionId) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionId", self.sessionId];
+  }
+  [self.eventsArray enumerateObjectsUsingBlock:^(Event *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"events"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasEnvironment) {
+    [output appendFormat:@"%@%@ {\n", indent, @"environment"];
+    [self.environment writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasJoiningDeviceIdentification) {
+    [output appendFormat:@"%@%@ {\n", indent, @"joiningDeviceIdentification"];
+    [self.joiningDeviceIdentification writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasJoiningDeviceSoftware) {
+    [output appendFormat:@"%@%@ {\n", indent, @"joiningDeviceSoftware"];
+    [self.joiningDeviceSoftware writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasAssistingDeviceIdentification) {
+    [output appendFormat:@"%@%@ {\n", indent, @"assistingDeviceIdentification"];
+    [self.assistingDeviceIdentification writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasAssistingDeviceSoftware) {
+    [output appendFormat:@"%@%@ {\n", indent, @"assistingDeviceSoftware"];
+    [self.assistingDeviceSoftware writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasAccountInfo) {
+    [output appendFormat:@"%@%@ {\n", indent, @"accountInfo"];
+    [self.accountInfo writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasFabricInfo) {
+    [output appendFormat:@"%@%@ {\n", indent, @"fabricInfo"];
+    [self.fabricInfo writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasSessionStartTimestampIso8601) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionStartTimestampIso8601", self.sessionStartTimestampIso8601];
+  }
+  if (self.hasSessionEndTimestampIso8601) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"sessionEndTimestampIso8601", self.sessionEndTimestampIso8601];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[WeavePairingSessionLog class]]) {
+    return NO;
+  }
+  WeavePairingSessionLog *otherMessage = other;
+  return
+      self.hasSessionStartTimestampMillis == otherMessage.hasSessionStartTimestampMillis &&
+      (!self.hasSessionStartTimestampMillis || self.sessionStartTimestampMillis == otherMessage.sessionStartTimestampMillis) &&
+      self.hasSessionEndTimestampMillis == otherMessage.hasSessionEndTimestampMillis &&
+      (!self.hasSessionEndTimestampMillis || self.sessionEndTimestampMillis == otherMessage.sessionEndTimestampMillis) &&
+      self.hasSessionStatus == otherMessage.hasSessionStatus &&
+      (!self.hasSessionStatus || self.sessionStatus == otherMessage.sessionStatus) &&
+      self.hasSessionId == otherMessage.hasSessionId &&
+      (!self.hasSessionId || [self.sessionId isEqual:otherMessage.sessionId]) &&
+      [self.eventsArray isEqualToArray:otherMessage.eventsArray] &&
+      self.hasEnvironment == otherMessage.hasEnvironment &&
+      (!self.hasEnvironment || [self.environment isEqual:otherMessage.environment]) &&
+      self.hasJoiningDeviceIdentification == otherMessage.hasJoiningDeviceIdentification &&
+      (!self.hasJoiningDeviceIdentification || [self.joiningDeviceIdentification isEqual:otherMessage.joiningDeviceIdentification]) &&
+      self.hasJoiningDeviceSoftware == otherMessage.hasJoiningDeviceSoftware &&
+      (!self.hasJoiningDeviceSoftware || [self.joiningDeviceSoftware isEqual:otherMessage.joiningDeviceSoftware]) &&
+      self.hasAssistingDeviceIdentification == otherMessage.hasAssistingDeviceIdentification &&
+      (!self.hasAssistingDeviceIdentification || [self.assistingDeviceIdentification isEqual:otherMessage.assistingDeviceIdentification]) &&
+      self.hasAssistingDeviceSoftware == otherMessage.hasAssistingDeviceSoftware &&
+      (!self.hasAssistingDeviceSoftware || [self.assistingDeviceSoftware isEqual:otherMessage.assistingDeviceSoftware]) &&
+      self.hasAccountInfo == otherMessage.hasAccountInfo &&
+      (!self.hasAccountInfo || [self.accountInfo isEqual:otherMessage.accountInfo]) &&
+      self.hasFabricInfo == otherMessage.hasFabricInfo &&
+      (!self.hasFabricInfo || [self.fabricInfo isEqual:otherMessage.fabricInfo]) &&
+      self.hasSessionStartTimestampIso8601 == otherMessage.hasSessionStartTimestampIso8601 &&
+      (!self.hasSessionStartTimestampIso8601 || [self.sessionStartTimestampIso8601 isEqual:otherMessage.sessionStartTimestampIso8601]) &&
+      self.hasSessionEndTimestampIso8601 == otherMessage.hasSessionEndTimestampIso8601 &&
+      (!self.hasSessionEndTimestampIso8601 || [self.sessionEndTimestampIso8601 isEqual:otherMessage.sessionEndTimestampIso8601]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasSessionStartTimestampMillis) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.sessionStartTimestampMillis] hash];
+  }
+  if (self.hasSessionEndTimestampMillis) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.sessionEndTimestampMillis] hash];
+  }
+  if (self.hasSessionStatus) {
+    hashCode = hashCode * 31 + self.sessionStatus;
+  }
+  if (self.hasSessionId) {
+    hashCode = hashCode * 31 + [self.sessionId hash];
+  }
+  [self.eventsArray enumerateObjectsUsingBlock:^(Event *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasEnvironment) {
+    hashCode = hashCode * 31 + [self.environment hash];
+  }
+  if (self.hasJoiningDeviceIdentification) {
+    hashCode = hashCode * 31 + [self.joiningDeviceIdentification hash];
+  }
+  if (self.hasJoiningDeviceSoftware) {
+    hashCode = hashCode * 31 + [self.joiningDeviceSoftware hash];
+  }
+  if (self.hasAssistingDeviceIdentification) {
+    hashCode = hashCode * 31 + [self.assistingDeviceIdentification hash];
+  }
+  if (self.hasAssistingDeviceSoftware) {
+    hashCode = hashCode * 31 + [self.assistingDeviceSoftware hash];
+  }
+  if (self.hasAccountInfo) {
+    hashCode = hashCode * 31 + [self.accountInfo hash];
+  }
+  if (self.hasFabricInfo) {
+    hashCode = hashCode * 31 + [self.fabricInfo hash];
+  }
+  if (self.hasSessionStartTimestampIso8601) {
+    hashCode = hashCode * 31 + [self.sessionStartTimestampIso8601 hash];
+  }
+  if (self.hasSessionEndTimestampIso8601) {
+    hashCode = hashCode * 31 + [self.sessionEndTimestampIso8601 hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL WeavePairingSessionLogStatusIsValidValue(WeavePairingSessionLogStatus value) {
+  switch (value) {
+    case WeavePairingSessionLogStatusUnknown:
+    case WeavePairingSessionLogStatusSuccess:
+    case WeavePairingSessionLogStatusFailure:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface WeavePairingSessionLogBuilder()
+@property (strong) WeavePairingSessionLog* result;
+@end
+
+@implementation WeavePairingSessionLogBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[WeavePairingSessionLog alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (WeavePairingSessionLogBuilder*) clear {
+  self.result = [[WeavePairingSessionLog alloc] init];
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clone {
+  return [WeavePairingSessionLog builderWithPrototype:result];
+}
+- (WeavePairingSessionLog*) defaultInstance {
+  return [WeavePairingSessionLog defaultInstance];
+}
+- (WeavePairingSessionLog*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (WeavePairingSessionLog*) buildPartial {
+  WeavePairingSessionLog* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (WeavePairingSessionLogBuilder*) mergeFrom:(WeavePairingSessionLog*) other {
+  if (other == [WeavePairingSessionLog defaultInstance]) {
+    return self;
+  }
+  if (other.hasSessionStartTimestampMillis) {
+    [self setSessionStartTimestampMillis:other.sessionStartTimestampMillis];
+  }
+  if (other.hasSessionEndTimestampMillis) {
+    [self setSessionEndTimestampMillis:other.sessionEndTimestampMillis];
+  }
+  if (other.hasSessionStatus) {
+    [self setSessionStatus:other.sessionStatus];
+  }
+  if (other.hasSessionId) {
+    [self setSessionId:other.sessionId];
+  }
+  if (other.eventsArray.count > 0) {
+    if (result.eventsArray == nil) {
+      result.eventsArray = [[NSMutableArray alloc] initWithArray:other.eventsArray];
+    } else {
+      [result.eventsArray addObjectsFromArray:other.eventsArray];
+    }
+  }
+  if (other.hasEnvironment) {
+    [self mergeEnvironment:other.environment];
+  }
+  if (other.hasJoiningDeviceIdentification) {
+    [self mergeJoiningDeviceIdentification:other.joiningDeviceIdentification];
+  }
+  if (other.hasJoiningDeviceSoftware) {
+    [self mergeJoiningDeviceSoftware:other.joiningDeviceSoftware];
+  }
+  if (other.hasAssistingDeviceIdentification) {
+    [self mergeAssistingDeviceIdentification:other.assistingDeviceIdentification];
+  }
+  if (other.hasAssistingDeviceSoftware) {
+    [self mergeAssistingDeviceSoftware:other.assistingDeviceSoftware];
+  }
+  if (other.hasAccountInfo) {
+    [self mergeAccountInfo:other.accountInfo];
+  }
+  if (other.hasFabricInfo) {
+    [self mergeFabricInfo:other.fabricInfo];
+  }
+  if (other.hasSessionStartTimestampIso8601) {
+    [self setSessionStartTimestampIso8601:other.sessionStartTimestampIso8601];
+  }
+  if (other.hasSessionEndTimestampIso8601) {
+    [self setSessionEndTimestampIso8601:other.sessionEndTimestampIso8601];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (WeavePairingSessionLogBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setSessionStartTimestampMillis:[input readSInt64]];
+        break;
+      }
+      case 16: {
+        [self setSessionEndTimestampMillis:[input readSInt64]];
+        break;
+      }
+      case 24: {
+        WeavePairingSessionLogStatus value = (WeavePairingSessionLogStatus)[input readEnum];
+        if (WeavePairingSessionLogStatusIsValidValue(value)) {
+          [self setSessionStatus:value];
+        } else {
+          [unknownFields mergeVarintField:3 value:value];
+        }
+        break;
+      }
+      case 34: {
+        [self setSessionId:[input readString]];
+        break;
+      }
+      case 42: {
+        EventBuilder* subBuilder = [Event builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addEvents:[subBuilder buildPartial]];
+        break;
+      }
+      case 50: {
+        EnvironmentBuilder* subBuilder = [Environment builder];
+        if (self.hasEnvironment) {
+          [subBuilder mergeFrom:self.environment];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setEnvironment:[subBuilder buildPartial]];
+        break;
+      }
+      case 58: {
+        IdentificationProfileBuilder* subBuilder = [IdentificationProfile builder];
+        if (self.hasJoiningDeviceIdentification) {
+          [subBuilder mergeFrom:self.joiningDeviceIdentification];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setJoiningDeviceIdentification:[subBuilder buildPartial]];
+        break;
+      }
+      case 66: {
+        SoftwareProfileBuilder* subBuilder = [SoftwareProfile builder];
+        if (self.hasJoiningDeviceSoftware) {
+          [subBuilder mergeFrom:self.joiningDeviceSoftware];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setJoiningDeviceSoftware:[subBuilder buildPartial]];
+        break;
+      }
+      case 74: {
+        IdentificationProfileBuilder* subBuilder = [IdentificationProfile builder];
+        if (self.hasAssistingDeviceIdentification) {
+          [subBuilder mergeFrom:self.assistingDeviceIdentification];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setAssistingDeviceIdentification:[subBuilder buildPartial]];
+        break;
+      }
+      case 82: {
+        SoftwareProfileBuilder* subBuilder = [SoftwareProfile builder];
+        if (self.hasAssistingDeviceSoftware) {
+          [subBuilder mergeFrom:self.assistingDeviceSoftware];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setAssistingDeviceSoftware:[subBuilder buildPartial]];
+        break;
+      }
+      case 90: {
+        AccountInfoBuilder* subBuilder = [AccountInfo builder];
+        if (self.hasAccountInfo) {
+          [subBuilder mergeFrom:self.accountInfo];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setAccountInfo:[subBuilder buildPartial]];
+        break;
+      }
+      case 98: {
+        FabricInfoBuilder* subBuilder = [FabricInfo builder];
+        if (self.hasFabricInfo) {
+          [subBuilder mergeFrom:self.fabricInfo];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setFabricInfo:[subBuilder buildPartial]];
+        break;
+      }
+      case 106: {
+        [self setSessionStartTimestampIso8601:[input readString]];
+        break;
+      }
+      case 114: {
+        [self setSessionEndTimestampIso8601:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasSessionStartTimestampMillis {
+  return result.hasSessionStartTimestampMillis;
+}
+- (SInt64) sessionStartTimestampMillis {
+  return result.sessionStartTimestampMillis;
+}
+- (WeavePairingSessionLogBuilder*) setSessionStartTimestampMillis:(SInt64) value {
+  result.hasSessionStartTimestampMillis = YES;
+  result.sessionStartTimestampMillis = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearSessionStartTimestampMillis {
+  result.hasSessionStartTimestampMillis = NO;
+  result.sessionStartTimestampMillis = 0L;
+  return self;
+}
+- (BOOL) hasSessionEndTimestampMillis {
+  return result.hasSessionEndTimestampMillis;
+}
+- (SInt64) sessionEndTimestampMillis {
+  return result.sessionEndTimestampMillis;
+}
+- (WeavePairingSessionLogBuilder*) setSessionEndTimestampMillis:(SInt64) value {
+  result.hasSessionEndTimestampMillis = YES;
+  result.sessionEndTimestampMillis = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearSessionEndTimestampMillis {
+  result.hasSessionEndTimestampMillis = NO;
+  result.sessionEndTimestampMillis = 0L;
+  return self;
+}
+- (BOOL) hasSessionStatus {
+  return result.hasSessionStatus;
+}
+- (WeavePairingSessionLogStatus) sessionStatus {
+  return result.sessionStatus;
+}
+- (WeavePairingSessionLogBuilder*) setSessionStatus:(WeavePairingSessionLogStatus) value {
+  result.hasSessionStatus = YES;
+  result.sessionStatus = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearSessionStatus {
+  result.hasSessionStatus = NO;
+  result.sessionStatus = WeavePairingSessionLogStatusUnknown;
+  return self;
+}
+- (BOOL) hasSessionId {
+  return result.hasSessionId;
+}
+- (NSString*) sessionId {
+  return result.sessionId;
+}
+- (WeavePairingSessionLogBuilder*) setSessionId:(NSString*) value {
+  result.hasSessionId = YES;
+  result.sessionId = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearSessionId {
+  result.hasSessionId = NO;
+  result.sessionId = @"";
+  return self;
+}
+- (NSMutableArray *)events {
+  return result.eventsArray;
+}
+- (Event*)eventsAtIndex:(NSUInteger)index {
+  return [result eventsAtIndex:index];
+}
+- (WeavePairingSessionLogBuilder *)addEvents:(Event*)value {
+  if (result.eventsArray == nil) {
+    result.eventsArray = [[NSMutableArray alloc]init];
+  }
+  [result.eventsArray addObject:value];
+  return self;
+}
+- (WeavePairingSessionLogBuilder *)setEventsArray:(NSArray *)array {
+  result.eventsArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (WeavePairingSessionLogBuilder *)clearEvents {
+  result.eventsArray = nil;
+  return self;
+}
+- (BOOL) hasEnvironment {
+  return result.hasEnvironment;
+}
+- (Environment*) environment {
+  return result.environment;
+}
+- (WeavePairingSessionLogBuilder*) setEnvironment:(Environment*) value {
+  result.hasEnvironment = YES;
+  result.environment = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) setEnvironmentBuilder:(EnvironmentBuilder*) builderForValue {
+  return [self setEnvironment:[builderForValue build]];
+}
+- (WeavePairingSessionLogBuilder*) mergeEnvironment:(Environment*) value {
+  if (result.hasEnvironment &&
+      result.environment != [Environment defaultInstance]) {
+    result.environment =
+      [[[Environment builderWithPrototype:result.environment] mergeFrom:value] buildPartial];
+  } else {
+    result.environment = value;
+  }
+  result.hasEnvironment = YES;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearEnvironment {
+  result.hasEnvironment = NO;
+  result.environment = [Environment defaultInstance];
+  return self;
+}
+- (BOOL) hasJoiningDeviceIdentification {
+  return result.hasJoiningDeviceIdentification;
+}
+- (IdentificationProfile*) joiningDeviceIdentification {
+  return result.joiningDeviceIdentification;
+}
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceIdentification:(IdentificationProfile*) value {
+  result.hasJoiningDeviceIdentification = YES;
+  result.joiningDeviceIdentification = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceIdentificationBuilder:(IdentificationProfileBuilder*) builderForValue {
+  return [self setJoiningDeviceIdentification:[builderForValue build]];
+}
+- (WeavePairingSessionLogBuilder*) mergeJoiningDeviceIdentification:(IdentificationProfile*) value {
+  if (result.hasJoiningDeviceIdentification &&
+      result.joiningDeviceIdentification != [IdentificationProfile defaultInstance]) {
+    result.joiningDeviceIdentification =
+      [[[IdentificationProfile builderWithPrototype:result.joiningDeviceIdentification] mergeFrom:value] buildPartial];
+  } else {
+    result.joiningDeviceIdentification = value;
+  }
+  result.hasJoiningDeviceIdentification = YES;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearJoiningDeviceIdentification {
+  result.hasJoiningDeviceIdentification = NO;
+  result.joiningDeviceIdentification = [IdentificationProfile defaultInstance];
+  return self;
+}
+- (BOOL) hasJoiningDeviceSoftware {
+  return result.hasJoiningDeviceSoftware;
+}
+- (SoftwareProfile*) joiningDeviceSoftware {
+  return result.joiningDeviceSoftware;
+}
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceSoftware:(SoftwareProfile*) value {
+  result.hasJoiningDeviceSoftware = YES;
+  result.joiningDeviceSoftware = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) setJoiningDeviceSoftwareBuilder:(SoftwareProfileBuilder*) builderForValue {
+  return [self setJoiningDeviceSoftware:[builderForValue build]];
+}
+- (WeavePairingSessionLogBuilder*) mergeJoiningDeviceSoftware:(SoftwareProfile*) value {
+  if (result.hasJoiningDeviceSoftware &&
+      result.joiningDeviceSoftware != [SoftwareProfile defaultInstance]) {
+    result.joiningDeviceSoftware =
+      [[[SoftwareProfile builderWithPrototype:result.joiningDeviceSoftware] mergeFrom:value] buildPartial];
+  } else {
+    result.joiningDeviceSoftware = value;
+  }
+  result.hasJoiningDeviceSoftware = YES;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearJoiningDeviceSoftware {
+  result.hasJoiningDeviceSoftware = NO;
+  result.joiningDeviceSoftware = [SoftwareProfile defaultInstance];
+  return self;
+}
+- (BOOL) hasAssistingDeviceIdentification {
+  return result.hasAssistingDeviceIdentification;
+}
+- (IdentificationProfile*) assistingDeviceIdentification {
+  return result.assistingDeviceIdentification;
+}
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceIdentification:(IdentificationProfile*) value {
+  result.hasAssistingDeviceIdentification = YES;
+  result.assistingDeviceIdentification = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceIdentificationBuilder:(IdentificationProfileBuilder*) builderForValue {
+  return [self setAssistingDeviceIdentification:[builderForValue build]];
+}
+- (WeavePairingSessionLogBuilder*) mergeAssistingDeviceIdentification:(IdentificationProfile*) value {
+  if (result.hasAssistingDeviceIdentification &&
+      result.assistingDeviceIdentification != [IdentificationProfile defaultInstance]) {
+    result.assistingDeviceIdentification =
+      [[[IdentificationProfile builderWithPrototype:result.assistingDeviceIdentification] mergeFrom:value] buildPartial];
+  } else {
+    result.assistingDeviceIdentification = value;
+  }
+  result.hasAssistingDeviceIdentification = YES;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearAssistingDeviceIdentification {
+  result.hasAssistingDeviceIdentification = NO;
+  result.assistingDeviceIdentification = [IdentificationProfile defaultInstance];
+  return self;
+}
+- (BOOL) hasAssistingDeviceSoftware {
+  return result.hasAssistingDeviceSoftware;
+}
+- (SoftwareProfile*) assistingDeviceSoftware {
+  return result.assistingDeviceSoftware;
+}
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceSoftware:(SoftwareProfile*) value {
+  result.hasAssistingDeviceSoftware = YES;
+  result.assistingDeviceSoftware = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) setAssistingDeviceSoftwareBuilder:(SoftwareProfileBuilder*) builderForValue {
+  return [self setAssistingDeviceSoftware:[builderForValue build]];
+}
+- (WeavePairingSessionLogBuilder*) mergeAssistingDeviceSoftware:(SoftwareProfile*) value {
+  if (result.hasAssistingDeviceSoftware &&
+      result.assistingDeviceSoftware != [SoftwareProfile defaultInstance]) {
+    result.assistingDeviceSoftware =
+      [[[SoftwareProfile builderWithPrototype:result.assistingDeviceSoftware] mergeFrom:value] buildPartial];
+  } else {
+    result.assistingDeviceSoftware = value;
+  }
+  result.hasAssistingDeviceSoftware = YES;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearAssistingDeviceSoftware {
+  result.hasAssistingDeviceSoftware = NO;
+  result.assistingDeviceSoftware = [SoftwareProfile defaultInstance];
+  return self;
+}
+- (BOOL) hasAccountInfo {
+  return result.hasAccountInfo;
+}
+- (AccountInfo*) accountInfo {
+  return result.accountInfo;
+}
+- (WeavePairingSessionLogBuilder*) setAccountInfo:(AccountInfo*) value {
+  result.hasAccountInfo = YES;
+  result.accountInfo = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) setAccountInfoBuilder:(AccountInfoBuilder*) builderForValue {
+  return [self setAccountInfo:[builderForValue build]];
+}
+- (WeavePairingSessionLogBuilder*) mergeAccountInfo:(AccountInfo*) value {
+  if (result.hasAccountInfo &&
+      result.accountInfo != [AccountInfo defaultInstance]) {
+    result.accountInfo =
+      [[[AccountInfo builderWithPrototype:result.accountInfo] mergeFrom:value] buildPartial];
+  } else {
+    result.accountInfo = value;
+  }
+  result.hasAccountInfo = YES;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearAccountInfo {
+  result.hasAccountInfo = NO;
+  result.accountInfo = [AccountInfo defaultInstance];
+  return self;
+}
+- (BOOL) hasFabricInfo {
+  return result.hasFabricInfo;
+}
+- (FabricInfo*) fabricInfo {
+  return result.fabricInfo;
+}
+- (WeavePairingSessionLogBuilder*) setFabricInfo:(FabricInfo*) value {
+  result.hasFabricInfo = YES;
+  result.fabricInfo = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) setFabricInfoBuilder:(FabricInfoBuilder*) builderForValue {
+  return [self setFabricInfo:[builderForValue build]];
+}
+- (WeavePairingSessionLogBuilder*) mergeFabricInfo:(FabricInfo*) value {
+  if (result.hasFabricInfo &&
+      result.fabricInfo != [FabricInfo defaultInstance]) {
+    result.fabricInfo =
+      [[[FabricInfo builderWithPrototype:result.fabricInfo] mergeFrom:value] buildPartial];
+  } else {
+    result.fabricInfo = value;
+  }
+  result.hasFabricInfo = YES;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearFabricInfo {
+  result.hasFabricInfo = NO;
+  result.fabricInfo = [FabricInfo defaultInstance];
+  return self;
+}
+- (BOOL) hasSessionStartTimestampIso8601 {
+  return result.hasSessionStartTimestampIso8601;
+}
+- (NSString*) sessionStartTimestampIso8601 {
+  return result.sessionStartTimestampIso8601;
+}
+- (WeavePairingSessionLogBuilder*) setSessionStartTimestampIso8601:(NSString*) value {
+  result.hasSessionStartTimestampIso8601 = YES;
+  result.sessionStartTimestampIso8601 = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearSessionStartTimestampIso8601 {
+  result.hasSessionStartTimestampIso8601 = NO;
+  result.sessionStartTimestampIso8601 = @"";
+  return self;
+}
+- (BOOL) hasSessionEndTimestampIso8601 {
+  return result.hasSessionEndTimestampIso8601;
+}
+- (NSString*) sessionEndTimestampIso8601 {
+  return result.sessionEndTimestampIso8601;
+}
+- (WeavePairingSessionLogBuilder*) setSessionEndTimestampIso8601:(NSString*) value {
+  result.hasSessionEndTimestampIso8601 = YES;
+  result.sessionEndTimestampIso8601 = value;
+  return self;
+}
+- (WeavePairingSessionLogBuilder*) clearSessionEndTimestampIso8601 {
+  result.hasSessionEndTimestampIso8601 = NO;
+  result.sessionEndTimestampIso8601 = @"";
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/runtime/Classes/AbstractMessage.h b/src/runtime/Classes/AbstractMessage.h
new file mode 100755
index 0000000..b3004c7
--- /dev/null
+++ b/src/runtime/Classes/AbstractMessage.h
@@ -0,0 +1,37 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Message.h"
+
+/**
+ * A partial implementation of the {@link Message} interface which implements
+ * as many methods of that interface as possible in terms of other methods.
+ *
+ * @author Cyrus Najmabadi
+ */
+@interface PBAbstractMessage : NSObject<PBMessage> {
+@private
+}
+
+/**
+ * Writes a string description of the message into the given mutable string
+ * respecting a given indent.
+ */
+- (void)writeDescriptionTo:(NSMutableString*) output
+                withIndent:(NSString*) indent;
+
+@end
diff --git a/src/runtime/Classes/AbstractMessage.m b/src/runtime/Classes/AbstractMessage.m
new file mode 100755
index 0000000..f819915
--- /dev/null
+++ b/src/runtime/Classes/AbstractMessage.m
@@ -0,0 +1,95 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "AbstractMessage.h"
+
+#import "CodedOutputStream.h"
+
+@implementation PBAbstractMessage
+
+- (id) init {
+  if ((self = [super init])) {
+  }
+
+  return self;
+}
+
+
+- (NSData*) data {
+  NSMutableData* data = [NSMutableData dataWithLength:self.serializedSize];
+  PBCodedOutputStream* stream = [PBCodedOutputStream streamWithData:data];
+  [self writeToCodedOutputStream:stream];
+  return data;
+}
+
+
+- (BOOL) isInitialized {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (SInt32) serializedSize {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (void) writeToOutputStream:(NSOutputStream*) output {
+  PBCodedOutputStream* codedOutput = [PBCodedOutputStream streamWithOutputStream:output];
+  [self writeToCodedOutputStream:codedOutput];
+  [codedOutput flush];
+}
+
+
+- (id<PBMessage>) defaultInstance {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (PBUnknownFieldSet*) unknownFields {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessageBuilder>) builder {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessageBuilder>) toBuilder {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (void) writeDescriptionTo:(NSMutableString*) output
+                 withIndent:(NSString*) indent {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (NSString*) description {
+  NSMutableString* output = [NSMutableString string];
+  [self writeDescriptionTo:output withIndent:@""];
+  return output;
+}
+
+
+@end
diff --git a/src/runtime/Classes/AbstractMessageBuilder.h b/src/runtime/Classes/AbstractMessageBuilder.h
new file mode 100755
index 0000000..9c454d4
--- /dev/null
+++ b/src/runtime/Classes/AbstractMessageBuilder.h
@@ -0,0 +1,29 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "MessageBuilder.h"
+
+/**
+ * A partial implementation of the {@link Message.Builder} interface which
+ * implements as many methods of that interface as possible in terms of
+ * other methods.
+ */
+@interface PBAbstractMessageBuilder : NSObject<PBMessageBuilder> {
+}
+
+@end
+
diff --git a/src/runtime/Classes/AbstractMessageBuilder.m b/src/runtime/Classes/AbstractMessageBuilder.m
new file mode 100755
index 0000000..1d162ef
--- /dev/null
+++ b/src/runtime/Classes/AbstractMessageBuilder.m
@@ -0,0 +1,123 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "AbstractMessageBuilder.h"
+
+#import "CodedInputStream.h"
+#import "ExtensionRegistry.h"
+#import "MessageBuilder.h"
+#import "UnknownFieldSet.h"
+#import "UnknownFieldSetBuilder.h"
+
+
+@implementation PBAbstractMessageBuilder
+
+- (id<PBMessageBuilder>) clone {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessageBuilder>) clear {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessageBuilder>) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+
+
+- (id<PBMessageBuilder>) mergeFromCodedInputStream:(PBCodedInputStream*) input
+                                  extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessageBuilder>) mergeUnknownFields:(PBUnknownFieldSet*) unknownFields {
+  PBUnknownFieldSet* merged =
+  [[[PBUnknownFieldSet builderWithUnknownFields:self.unknownFields]
+    mergeUnknownFields:unknownFields] build];
+
+  [self setUnknownFields:merged];
+  return self;
+}
+
+
+- (id<PBMessageBuilder>) mergeFromData:(NSData*) data {
+  PBCodedInputStream* input = [PBCodedInputStream streamWithData:data];
+  [self mergeFromCodedInputStream:input];
+  [input checkLastTagWas:0];
+  return self;
+}
+
+
+- (id<PBMessageBuilder>) mergeFromData:(NSData*) data
+                      extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBCodedInputStream* input = [PBCodedInputStream streamWithData:data];
+  [self mergeFromCodedInputStream:input extensionRegistry:extensionRegistry];
+  [input checkLastTagWas:0];
+  return self;
+}
+
+
+- (id<PBMessageBuilder>) mergeFromInputStream:(NSInputStream*) input {
+  PBCodedInputStream* codedInput = [PBCodedInputStream streamWithInputStream:input];
+  [self mergeFromCodedInputStream:codedInput];
+  [codedInput checkLastTagWas:0];
+  return self;
+}
+
+
+- (id<PBMessageBuilder>) mergeFromInputStream:(NSInputStream*) input
+                             extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBCodedInputStream* codedInput = [PBCodedInputStream streamWithInputStream:input];
+  [self mergeFromCodedInputStream:codedInput extensionRegistry:extensionRegistry];
+  [codedInput checkLastTagWas:0];
+  return self;
+}
+
+
+- (id<PBMessage>) build {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessage>) buildPartial {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (BOOL) isInitialized {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessage>) defaultInstance {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (PBUnknownFieldSet*) unknownFields {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (id<PBMessageBuilder>) setUnknownFields:(PBUnknownFieldSet*) unknownFields {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+@end
diff --git a/src/runtime/Classes/Bootstrap.h b/src/runtime/Classes/Bootstrap.h
new file mode 100755
index 0000000..8928c1a
--- /dev/null
+++ b/src/runtime/Classes/Bootstrap.h
@@ -0,0 +1,30 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "ForwardDeclarations.h"
+
+#import "CodedInputStream.h"
+#import "CodedOutputStream.h"
+#import "ExtendableMessage.h"
+#import "ExtendableMessageBuilder.h"
+#import "ExtensionRegistry.h"
+#import "GeneratedMessage.h"
+#import "GeneratedMessageBuilder.h"
+#import "MessageBuilder.h"
+#import "UnknownFieldSet.h"
+#import "UnknownFieldSetBuilder.h"
+#import "Utilities.h"
diff --git a/src/runtime/Classes/CodedInputStream.h b/src/runtime/Classes/CodedInputStream.h
new file mode 100755
index 0000000..0170cb4
--- /dev/null
+++ b/src/runtime/Classes/CodedInputStream.h
@@ -0,0 +1,166 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+@class PBExtensionRegistry;
+@class PBUnknownFieldSetBuilder;
+@protocol PBMessageBuilder;
+
+/**
+ * Reads and decodes protocol message fields.
+ *
+ * This class contains two kinds of methods:  methods that read specific
+ * protocol message constructs and field types (e.g. {@link #readTag()} and
+ * {@link #readInt32()}) and methods that read low-level values (e.g.
+ * {@link #readRawVarint32()} and {@link #readRawBytes}).  If you are reading
+ * encoded protocol messages, you should use the former methods, but if you are
+ * reading some other format of your own design, use the latter.
+ *
+ * @author Cyrus Najmabadi
+ */
+@interface PBCodedInputStream : NSObject {
+@private
+  NSMutableData* buffer;
+  SInt32 bufferSize;
+  SInt32 bufferSizeAfterLimit;
+  SInt32 bufferPos;
+  NSInputStream* input;
+  SInt32 lastTag;
+
+  /**
+   * The total number of bytes read before the current buffer.  The total
+   * bytes read up to the current position can be computed as
+   * {@code totalBytesRetired + bufferPos}.
+   */
+  SInt32 totalBytesRetired;
+
+  /** The absolute position of the end of the current message. */
+  SInt32 currentLimit;
+
+  /** See setRecursionLimit() */
+  SInt32 recursionDepth;
+  SInt32 recursionLimit;
+
+  /** See setSizeLimit() */
+  SInt32 sizeLimit;
+}
+
++ (PBCodedInputStream*) streamWithData:(NSData*) data;
++ (PBCodedInputStream*) streamWithInputStream:(NSInputStream*) input;
+
+/**
+ * Attempt to read a field tag, returning zero if we have reached EOF.
+ * Protocol message parsers use this to read tags, since a protocol message
+ * may legally end wherever a tag occurs, and zero is not a valid tag number.
+ */
+- (SInt32) readTag;
+- (BOOL) refillBuffer:(BOOL) mustSucceed;
+
+- (Float64) readDouble;
+- (Float32) readFloat;
+- (SInt64) readUInt64;
+- (SInt32) readUInt32;
+- (SInt64) readInt64;
+- (SInt32) readInt32;
+- (SInt64) readFixed64;
+- (SInt32) readFixed32;
+- (SInt32) readEnum;
+- (SInt32) readSFixed32;
+- (SInt64) readSFixed64;
+- (SInt32) readSInt32;
+- (SInt64) readSInt64;
+
+/**
+ * Read one byte from the input.
+ *
+ * @throws InvalidProtocolBuffer The end of the stream or the current
+ *                                        limit was reached.
+ */
+- (int8_t) readRawByte;
+
+/**
+ * Read a raw Varint from the stream.  If larger than 32 bits, discard the
+ * upper bits.
+ */
+- (SInt32) readRawVarint32;
+- (SInt64) readRawVarint64;
+- (SInt32) readRawLittleEndian32;
+- (SInt64) readRawLittleEndian64;
+
+/**
+ * Read a fixed size of bytes from the input.
+ *
+ * @throws InvalidProtocolBuffer The end of the stream or the current
+ *                                        limit was reached.
+ */
+- (NSData*) readRawData:(SInt32) size;
+
+/**
+ * Reads and discards a single field, given its tag value.
+ *
+ * @return {@code false} if the tag is an endgroup tag, in which case
+ *         nothing is skipped.  Otherwise, returns {@code true}.
+ */
+- (BOOL) skipField:(SInt32) tag;
+
+
+/**
+ * Reads and discards {@code size} bytes.
+ *
+ * @throws InvalidProtocolBuffer The end of the stream or the current
+ *                                        limit was reached.
+ */
+- (void) skipRawData:(SInt32) size;
+
+/**
+ * Reads and discards an entire message.  This will read either until EOF
+ * or until an endgroup tag, whichever comes first.
+ */
+- (void) skipMessage;
+
+- (BOOL) isAtEnd;
+- (SInt32) pushLimit:(SInt32) byteLimit;
+- (void) recomputeBufferSizeAfterLimit;
+- (void) popLimit:(SInt32) oldLimit;
+- (SInt32) bytesUntilLimit;
+
+
+/** Read an embedded message field value from the stream. */
+- (void) readMessage:(id<PBMessageBuilder>) builder extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) readBool;
+- (NSString*) readString;
+- (NSData*) readData;
+
+- (void) readGroup:(SInt32) fieldNumber builder:(id<PBMessageBuilder>) builder extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+/**
+ * Reads a {@code group} field value from the stream and merges it into the
+ * given {@link UnknownFieldSet}.
+ */
+- (void) readUnknownGroup:(SInt32) fieldNumber builder:(PBUnknownFieldSetBuilder*) builder;
+
+/**
+ * Verifies that the last call to readTag() returned the given tag value.
+ * This is used to verify that a nested group ended with the correct
+ * end tag.
+ *
+ * @throws InvalidProtocolBuffer {@code value} does not match the
+ *                                        last tag.
+ */
+- (void) checkLastTagWas:(SInt32) value;
+
+@end
diff --git a/src/runtime/Classes/CodedInputStream.m b/src/runtime/Classes/CodedInputStream.m
new file mode 100755
index 0000000..47d2450
--- /dev/null
+++ b/src/runtime/Classes/CodedInputStream.m
@@ -0,0 +1,763 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "CodedInputStream.h"
+
+#import "MessageBuilder.h"
+#import "Utilities.h"
+#import "WireFormat.h"
+#import "UnknownFieldSetBuilder.h"
+#import "UnknownFieldSet.h"
+
+
+@interface PBCodedInputStream ()
+@property (strong) NSMutableData* buffer;
+@property (strong) NSInputStream* input;
+@end
+
+
+@implementation PBCodedInputStream
+
+const SInt32 DEFAULT_RECURSION_LIMIT = 64;
+const SInt32 DEFAULT_SIZE_LIMIT = 64 << 20;  // 64MB
+const SInt32 BUFFER_SIZE = 4096;
+
+@synthesize buffer;
+@synthesize input;
+
+
+
+
+- (void) commonInit {
+  currentLimit = INT_MAX;
+  recursionLimit = DEFAULT_RECURSION_LIMIT;
+  sizeLimit = DEFAULT_SIZE_LIMIT;
+}
+
+
+- (id) initWithData:(NSData*) data {
+  if ((self = [super init])) {
+    self.buffer = [NSMutableData dataWithData:data];
+    bufferSize = (UInt32)buffer.length;
+    self.input = nil;
+    [self commonInit];
+  }
+
+  return self;
+}
+
+
+- (id) initWithInputStream:(NSInputStream*) input_ {
+  if ((self = [super init])) {
+    self.buffer = [NSMutableData dataWithLength:BUFFER_SIZE];
+    bufferSize = 0;
+    self.input = input_;
+    [input open];
+    [self commonInit];
+  }
+
+  return self;
+}
+
+
++ (PBCodedInputStream*) streamWithData:(NSData*) data {
+    return [[PBCodedInputStream alloc] initWithData:data];
+}
+
+
++ (PBCodedInputStream*) streamWithInputStream:(NSInputStream*) input {
+    return [[PBCodedInputStream alloc] initWithInputStream:input];
+}
+
+
+/**
+ * Attempt to read a field tag, returning zero if we have reached EOF.
+ * Protocol message parsers use this to read tags, since a protocol message
+ * may legally end wherever a tag occurs, and zero is not a valid tag number.
+ */
+- (SInt32) readTag {
+  if (self.isAtEnd) {
+    lastTag = 0;
+    return 0;
+  }
+
+  lastTag = [self readRawVarint32];
+  if (lastTag == 0) {
+    // If we actually read zero, that's not a valid tag.
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"Invalid Tag" userInfo:nil];
+  }
+  return lastTag;
+}
+
+/**
+ * Verifies that the last call to readTag() returned the given tag value.
+ * This is used to verify that a nested group ended with the correct
+ * end tag.
+ *
+ * @throws InvalidProtocolBufferException {@code value} does not match the
+ *                                        last tag.
+ */
+- (void) checkLastTagWas:(SInt32) value {
+  if (lastTag != value) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"Invalid End Tag" userInfo:nil];
+  }
+}
+
+/**
+ * Reads and discards a single field, given its tag value.
+ *
+ * @return {@code NO} if the tag is an endgroup tag, in which case
+ *         nothing is skipped.  Otherwise, returns {@code YES}.
+ */
+- (BOOL) skipField:(SInt32) tag {
+  switch (PBWireFormatGetTagWireType(tag)) {
+    case PBWireFormatVarint:
+      [self readInt32];
+      return YES;
+    case PBWireFormatFixed64:
+      [self readRawLittleEndian64];
+      return YES;
+    case PBWireFormatLengthDelimited:
+      [self skipRawData:[self readRawVarint32]];
+      return YES;
+    case PBWireFormatStartGroup:
+      [self skipMessage];
+      [self checkLastTagWas:
+       PBWireFormatMakeTag(PBWireFormatGetTagFieldNumber(tag),
+                           PBWireFormatEndGroup)];
+      return YES;
+    case PBWireFormatEndGroup:
+      return NO;
+    case PBWireFormatFixed32:
+      [self readRawLittleEndian32];
+      return YES;
+    default:
+      @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"Invalid Wire Type" userInfo:nil];
+  }
+}
+
+
+/**
+ * Reads and discards an entire message.  This will read either until EOF
+ * or until an endgroup tag, whichever comes first.
+ */
+- (void) skipMessage {
+  while (YES) {
+    SInt32 tag = [self readTag];
+    if (tag == 0 || ![self skipField:tag]) {
+      return;
+    }
+  }
+}
+
+
+/** Read a {@code double} field value from the stream. */
+- (Float64) readDouble {
+  return convertInt64ToFloat64([self readRawLittleEndian64]);
+}
+
+
+/** Read a {@code float} field value from the stream. */
+- (Float32) readFloat {
+  return convertInt32ToFloat32([self readRawLittleEndian32]);
+}
+
+
+/** Read a {@code uint64} field value from the stream. */
+- (SInt64) readUInt64 {
+  return [self readRawVarint64];
+}
+
+
+/** Read an {@code int64} field value from the stream. */
+- (SInt64) readInt64 {
+  return [self readRawVarint64];
+}
+
+
+/** Read an {@code int32} field value from the stream. */
+- (SInt32) readInt32 {
+  return [self readRawVarint32];
+}
+
+
+/** Read a {@code fixed64} field value from the stream. */
+- (SInt64) readFixed64 {
+  return [self readRawLittleEndian64];
+}
+
+
+/** Read a {@code fixed32} field value from the stream. */
+- (SInt32) readFixed32 {
+  return [self readRawLittleEndian32];
+}
+
+
+/** Read a {@code bool} field value from the stream. */
+- (BOOL) readBool {
+  return [self readRawVarint32] != 0;
+}
+
+
+/** Read a {@code string} field value from the stream. */
+- (NSString*) readString {
+  SInt32 size = [self readRawVarint32];
+  if (size <= (bufferSize - bufferPos) && size > 0) {
+    // Fast path:  We already have the bytes in a contiguous buffer, so
+    //   just copy directly from it.
+    //  new String(buffer, bufferPos, size, "UTF-8");
+    NSString* result = [[NSString alloc] initWithBytes:(((uint8_t*) buffer.bytes) + bufferPos)
+                                                 length:size
+                                               encoding:NSUTF8StringEncoding];
+    bufferPos += size;
+    return result;
+  } else {
+    // Slow path:  Build a byte array first then copy it.
+    NSData* data = [self readRawData:size];
+      return [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
+  }
+}
+
+
+/** Read a {@code group} field value from the stream. */
+- (void)      readGroup:(SInt32) fieldNumber
+                builder:(id<PBMessageBuilder>) builder
+      extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  if (recursionDepth >= recursionLimit) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"Recursion Limit Exceeded" userInfo:nil];
+  }
+  ++recursionDepth;
+  [builder mergeFromCodedInputStream:self extensionRegistry:extensionRegistry];
+  [self checkLastTagWas:PBWireFormatMakeTag(fieldNumber, PBWireFormatEndGroup)];
+  --recursionDepth;
+}
+
+
+/**
+ * Reads a {@code group} field value from the stream and merges it into the
+ * given {@link PBUnknownFieldSet}.
+ */
+- (void) readUnknownGroup:(SInt32) fieldNumber
+                  builder:(PBUnknownFieldSetBuilder*) builder {
+  if (recursionDepth >= recursionLimit) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"Recursion Limit Exceeded" userInfo:nil];
+  }
+  ++recursionDepth;
+  [builder mergeFromCodedInputStream:self];
+  [self checkLastTagWas:PBWireFormatMakeTag(fieldNumber, PBWireFormatEndGroup)];
+  --recursionDepth;
+}
+
+
+/** Read an embedded message field value from the stream. */
+- (void) readMessage:(id<PBMessageBuilder>) builder
+   extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  SInt32 length = [self readRawVarint32];
+  if (recursionDepth >= recursionLimit) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"Recursion Limit Exceeded" userInfo:nil];
+  }
+  SInt32 oldLimit = [self pushLimit:length];
+  ++recursionDepth;
+  [builder mergeFromCodedInputStream:self extensionRegistry:extensionRegistry];
+  [self checkLastTagWas:0];
+  --recursionDepth;
+  [self popLimit:oldLimit];
+}
+
+
+/** Read a {@code bytes} field value from the stream. */
+- (NSData*) readData {
+  SInt32 size = [self readRawVarint32];
+  if (size < bufferSize - bufferPos && size > 0) {
+    // Fast path:  We already have the bytes in a contiguous buffer, so
+    //   just copy directly from it.
+    NSData* result = [NSData dataWithBytes:(((uint8_t*) buffer.bytes) + bufferPos) length:size];
+    bufferPos += size;
+    return result;
+  } else {
+    // Slow path:  Build a byte array first then copy it.
+    return [self readRawData:size];
+  }
+}
+
+
+/** Read a {@code uint32} field value from the stream. */
+- (SInt32) readUInt32 {
+  return [self readRawVarint32];
+}
+
+
+/**
+ * Read an enum field value from the stream.  Caller is responsible
+ * for converting the numeric value to an actual enum.
+ */
+- (SInt32) readEnum {
+  return [self readRawVarint32];
+}
+
+
+/** Read an {@code sfixed32} field value from the stream. */
+- (SInt32) readSFixed32 {
+  return [self readRawLittleEndian32];
+}
+
+
+/** Read an {@code sfixed64} field value from the stream. */
+- (SInt64) readSFixed64 {
+  return [self readRawLittleEndian64];
+}
+
+
+/** Read an {@code sint32} field value from the stream. */
+- (SInt32) readSInt32 {
+  return decodeZigZag32([self readRawVarint32]);
+}
+
+
+/** Read an {@code sint64} field value from the stream. */
+- (SInt64) readSInt64 {
+  return decodeZigZag64([self readRawVarint64]);
+}
+
+
+// =================================================================
+
+/**
+ * Read a raw Varint from the stream.  If larger than 32 bits, discard the
+ * upper bits.
+ */
+- (SInt32) readRawVarint32 {
+  int8_t tmp = [self readRawByte];
+  if (tmp >= 0) {
+    return tmp;
+  }
+  SInt32 result = tmp & 0x7f;
+  if ((tmp = [self readRawByte]) >= 0) {
+    result |= tmp << 7;
+  } else {
+    result |= (tmp & 0x7f) << 7;
+    if ((tmp = [self readRawByte]) >= 0) {
+      result |= tmp << 14;
+    } else {
+      result |= (tmp & 0x7f) << 14;
+      if ((tmp = [self readRawByte]) >= 0) {
+        result |= tmp << 21;
+      } else {
+        result |= (tmp & 0x7f) << 21;
+        result |= (tmp = [self readRawByte]) << 28;
+        if (tmp < 0) {
+          // Discard upper 32 bits.
+          for (int i = 0; i < 5; i++) {
+            if ([self readRawByte] >= 0) {
+              return result;
+            }
+          }
+          @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"malformedVarint" userInfo:nil];
+        }
+      }
+    }
+  }
+  return result;
+}
+
+
+/** Read a raw Varint from the stream. */
+- (SInt64) readRawVarint64 {
+  SInt32 shift = 0;
+  SInt64 result = 0;
+  while (shift < 64) {
+    int8_t b = [self readRawByte];
+    result |= (SInt64)(b & 0x7F) << shift;
+    if ((b & 0x80) == 0) {
+      return result;
+    }
+    shift += 7;
+  }
+  @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"malformedVarint" userInfo:nil];
+}
+
+
+/** Read a 32-bit little-endian integer from the stream. */
+- (SInt32) readRawLittleEndian32 {
+  int8_t b1 = [self readRawByte];
+  int8_t b2 = [self readRawByte];
+  int8_t b3 = [self readRawByte];
+  int8_t b4 = [self readRawByte];
+  return
+  (((SInt32)b1 & 0xff)      ) |
+  (((SInt32)b2 & 0xff) <<  8) |
+  (((SInt32)b3 & 0xff) << 16) |
+  (((SInt32)b4 & 0xff) << 24);
+}
+
+
+/** Read a 64-bit little-endian integer from the stream. */
+- (SInt64) readRawLittleEndian64 {
+  int8_t b1 = [self readRawByte];
+  int8_t b2 = [self readRawByte];
+  int8_t b3 = [self readRawByte];
+  int8_t b4 = [self readRawByte];
+  int8_t b5 = [self readRawByte];
+  int8_t b6 = [self readRawByte];
+  int8_t b7 = [self readRawByte];
+  int8_t b8 = [self readRawByte];
+  return
+  (((SInt64)b1 & 0xff)      ) |
+  (((SInt64)b2 & 0xff) <<  8) |
+  (((SInt64)b3 & 0xff) << 16) |
+  (((SInt64)b4 & 0xff) << 24) |
+  (((SInt64)b5 & 0xff) << 32) |
+  (((SInt64)b6 & 0xff) << 40) |
+  (((SInt64)b7 & 0xff) << 48) |
+  (((SInt64)b8 & 0xff) << 56);
+}
+
+
+/**
+ * Set the maximum message recursion depth.  In order to prevent malicious
+ * messages from causing stack overflows, {@code PBCodedInputStream} limits
+ * how deeply messages may be nested.  The default limit is 64.
+ *
+ * @return the old limit.
+ */
+- (SInt32) setRecursionLimit:(SInt32) limit {
+  if (limit < 0) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Recursion limit cannot be negative" userInfo:nil];
+  }
+  SInt32 oldLimit = recursionLimit;
+  recursionLimit = limit;
+  return oldLimit;
+}
+
+
+/**
+ * Set the maximum message size.  In order to prevent malicious
+ * messages from exhausting memory or causing integer overflows,
+ * {@code PBCodedInputStream} limits how large a message may be.
+ * The default limit is 64MB.  You should set this limit as small
+ * as you can without harming your app's functionality.  Note that
+ * size limits only apply when reading from an {@code InputStream}, not
+ * when constructed around a raw byte array.
+ *
+ * @return the old limit.
+ */
+- (SInt32) setSizeLimit:(SInt32) limit {
+  if (limit < 0) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Size limit cannot be negative:" userInfo:nil];
+  }
+  SInt32 oldLimit = sizeLimit;
+  sizeLimit = limit;
+  return oldLimit;
+}
+
+
+/**
+ * Resets the current size counter to zero (see {@link #setSizeLimit(int)}).
+ */
+- (void) resetSizeCounter {
+  totalBytesRetired = 0;
+}
+
+
+/**
+ * Sets {@code currentLimit} to (current position) + {@code byteLimit}.  This
+ * is called when descending into a length-delimited embedded message.
+ *
+ * @return the old limit.
+ */
+- (SInt32) pushLimit:(SInt32) byteLimit {
+  if (byteLimit < 0) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"negativeSize" userInfo:nil];
+  }
+  byteLimit += totalBytesRetired + bufferPos;
+  SInt32 oldLimit = currentLimit;
+  if (byteLimit > oldLimit) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"truncatedMessage" userInfo:nil];
+  }
+  currentLimit = byteLimit;
+
+  [self recomputeBufferSizeAfterLimit];
+
+  return oldLimit;
+}
+
+
+- (void) recomputeBufferSizeAfterLimit {
+  bufferSize += bufferSizeAfterLimit;
+  SInt32 bufferEnd = totalBytesRetired + bufferSize;
+  if (bufferEnd > currentLimit) {
+    // Limit is in current buffer.
+    bufferSizeAfterLimit = bufferEnd - currentLimit;
+    bufferSize -= bufferSizeAfterLimit;
+  } else {
+    bufferSizeAfterLimit = 0;
+  }
+}
+
+
+/**
+ * Discards the current limit, returning to the previous limit.
+ *
+ * @param oldLimit The old limit, as returned by {@code pushLimit}.
+ */
+- (void) popLimit:(SInt32) oldLimit {
+  currentLimit = oldLimit;
+  [self recomputeBufferSizeAfterLimit];
+}
+
+
+/**
+ * Returns the number of bytes to be read before the current limit.
+ * If no limit is set, returns -1.
+ */
+- (SInt32) bytesUntilLimit {
+  if (currentLimit == INT_MAX) {
+    return -1;
+  }
+
+  SInt32 currentAbsolutePosition = totalBytesRetired + bufferPos;
+  return currentLimit - currentAbsolutePosition;
+}
+
+/**
+ * Returns true if the stream has reached the end of the input.  This is the
+ * case if either the end of the underlying input source has been reached or
+ * if the stream has reached a limit created using {@link #pushLimit(int)}.
+ */
+- (BOOL) isAtEnd {
+  return bufferPos == bufferSize && ![self refillBuffer:NO];
+}
+
+
+/**
+ * Called with {@code this.buffer} is empty to read more bytes from the
+ * input.  If {@code mustSucceed} is YES, refillBuffer() gurantees that
+ * either there will be at least one byte in the buffer when it returns
+ * or it will throw an exception.  If {@code mustSucceed} is NO,
+ * refillBuffer() returns NO if no more bytes were available.
+ */
+- (BOOL) refillBuffer:(BOOL) mustSucceed {
+  if (bufferPos < bufferSize) {
+    @throw [NSException exceptionWithName:@"IllegalState" reason:@"refillBuffer called when buffer wasn't empty." userInfo:nil];
+  }
+
+  if (totalBytesRetired + bufferSize == currentLimit) {
+    // Oops, we hit a limit.
+    if (mustSucceed) {
+      @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"truncatedMessage" userInfo:nil];
+    } else {
+      return NO;
+    }
+  }
+
+  totalBytesRetired += bufferSize;
+
+  // TODO(cyrusn): does NSInputStream behave the same as java.io.InputStream
+  // when there is no more data?
+  bufferPos = 0;
+  bufferSize = 0;
+  if (input != nil) {
+    bufferSize = (SInt32)[input read:buffer.mutableBytes maxLength:buffer.length];
+  }
+
+  if (bufferSize <= 0) {
+    bufferSize = 0;
+    if (mustSucceed) {
+      @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"truncatedMessage" userInfo:nil];
+    } else {
+      return NO;
+    }
+  } else {
+    [self recomputeBufferSizeAfterLimit];
+    SInt32 totalBytesRead = totalBytesRetired + bufferSize + bufferSizeAfterLimit;
+    if (totalBytesRead > sizeLimit || totalBytesRead < 0) {
+      @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"sizeLimitExceeded" userInfo:nil];
+    }
+    return YES;
+  }
+}
+
+
+/**
+ * Read one byte from the input.
+ *
+ * @throws InvalidProtocolBufferException The end of the stream or the current
+ *                                        limit was reached.
+ */
+- (int8_t) readRawByte {
+  if (bufferPos == bufferSize) {
+    [self refillBuffer:YES];
+  }
+  int8_t* bytes = (int8_t*)buffer.bytes;
+  return bytes[bufferPos++];
+}
+
+
+/**
+ * Read a fixed size of bytes from the input.
+ *
+ * @throws InvalidProtocolBufferException The end of the stream or the current
+ *                                        limit was reached.
+ */
+- (NSData*) readRawData:(SInt32) size {
+  if (size < 0) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"negativeSize" userInfo:nil];
+  }
+
+  if (totalBytesRetired + bufferPos + size > currentLimit) {
+    // Read to the end of the stream anyway.
+    [self skipRawData:currentLimit - totalBytesRetired - bufferPos];
+    // Then fail.
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"truncatedMessage" userInfo:nil];
+  }
+
+  if (size <= bufferSize - bufferPos) {
+    // We have all the bytes we need already.
+    NSData* data = [NSData dataWithBytes:(((int8_t*) buffer.bytes) + bufferPos) length:size];
+    bufferPos += size;
+    return data;
+  } else if (size < BUFFER_SIZE) {
+    // Reading more bytes than are in the buffer, but not an excessive number
+    // of bytes.  We can safely allocate the resulting array ahead of time.
+
+    // First copy what we have.
+    NSMutableData* bytes = [NSMutableData dataWithLength:size];
+    SInt32 pos = bufferSize - bufferPos;
+    memcpy(bytes.mutableBytes, ((int8_t*)buffer.bytes) + bufferPos, pos);
+    bufferPos = bufferSize;
+
+    // We want to use refillBuffer() and then copy from the buffer into our
+    // byte array rather than reading directly into our byte array because
+    // the input may be unbuffered.
+    [self refillBuffer:YES];
+
+    while (size - pos > bufferSize) {
+      memcpy(((int8_t*)bytes.mutableBytes) + pos, buffer.bytes, bufferSize);
+      pos += bufferSize;
+      bufferPos = bufferSize;
+      [self refillBuffer:YES];
+    }
+
+    memcpy(((int8_t*)bytes.mutableBytes) + pos, buffer.bytes, size - pos);
+    bufferPos = size - pos;
+
+    return bytes;
+  } else {
+    // The size is very large.  For security reasons, we can't allocate the
+    // entire byte array yet.  The size comes directly from the input, so a
+    // maliciously-crafted message could provide a bogus very large size in
+    // order to trick the app into allocating a lot of memory.  We avoid this
+    // by allocating and reading only a small chunk at a time, so that the
+    // malicious message must actuall* e* extremely large to cause
+    // problems.  Meanwhile, we limit the allowed size of a message elsewhere.
+
+    // Remember the buffer markers since we'll have to copy the bytes out of
+    // it later.
+    SInt32 originalBufferPos = bufferPos;
+    SInt32 originalBufferSize = bufferSize;
+
+    // Mark the current buffer consumed.
+    totalBytesRetired += bufferSize;
+    bufferPos = 0;
+    bufferSize = 0;
+
+    // Read all the rest of the bytes we need.
+    SInt32 sizeLeft = size - (originalBufferSize - originalBufferPos);
+    NSMutableArray* chunks = [NSMutableArray array];
+
+    while (sizeLeft > 0) {
+      NSMutableData* chunk = [NSMutableData dataWithLength:MIN(sizeLeft, BUFFER_SIZE)];
+
+      SInt32 pos = 0;
+      while (pos < chunk.length) {
+        SInt32 n = 0;
+        if (input != nil) {
+          n = (SInt32)[input read:(((uint8_t*) chunk.mutableBytes) + pos) maxLength:chunk.length - pos];
+        }
+        if (n <= 0) {
+          @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"truncatedMessage" userInfo:nil];
+        }
+        totalBytesRetired += n;
+        pos += n;
+      }
+      sizeLeft -= chunk.length;
+      [chunks addObject:chunk];
+    }
+
+    // OK, got everything.  Now concatenate it all into one buffer.
+    NSMutableData* bytes = [NSMutableData dataWithLength:size];
+
+    // Start by copying the leftover bytes from this.buffer.
+    SInt32 pos = originalBufferSize - originalBufferPos;
+    memcpy(bytes.mutableBytes, ((int8_t*)buffer.bytes) + originalBufferPos, pos);
+
+    // And now all the chunks.
+    for (NSData* chunk in chunks) {
+      memcpy(((int8_t*)bytes.mutableBytes) + pos, chunk.bytes, chunk.length);
+      pos += chunk.length;
+    }
+
+    // Done.
+    return bytes;
+  }
+}
+
+
+/**
+ * Reads and discards {@code size} bytes.
+ *
+ * @throws InvalidProtocolBufferException The end of the stream or the current
+ *                                        limit was reached.
+ */
+- (void) skipRawData:(SInt32) size {
+  if (size < 0) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"negativeSize" userInfo:nil];
+  }
+
+  if (totalBytesRetired + bufferPos + size > currentLimit) {
+    // Read to the end of the stream anyway.
+    [self skipRawData:currentLimit - totalBytesRetired - bufferPos];
+    // Then fail.
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"truncatedMessage" userInfo:nil];
+  }
+
+  if (size <= (bufferSize - bufferPos)) {
+    // We have all the bytes we need already.
+    bufferPos += size;
+  } else {
+    // Skipping more bytes than are in the buffer.  First skip what we have.
+    SInt32 pos = bufferSize - bufferPos;
+    totalBytesRetired += pos;
+    bufferPos = 0;
+    bufferSize = 0;
+
+    // Then skip directly from the InputStream for the rest.
+    while (pos < size) {
+      NSMutableData* data = [NSMutableData dataWithLength:(size - pos)];
+      SInt32 n = (input == nil) ? -1 : (SInt32)[input read:data.mutableBytes maxLength:(size - pos)];
+      if (n <= 0) {
+        @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"truncatedMessage" userInfo:nil];
+      }
+      pos += n;
+      totalBytesRetired += n;
+    }
+  }
+}
+
+
+
+@end
diff --git a/src/runtime/Classes/CodedOutputStream.h b/src/runtime/Classes/CodedOutputStream.h
new file mode 100755
index 0000000..d9f47a4
--- /dev/null
+++ b/src/runtime/Classes/CodedOutputStream.h
@@ -0,0 +1,137 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+/**
+ * Encodes and writes protocol message fields.
+ *
+ * <p>This class contains two kinds of methods:  methods that write specific
+ * protocol message constructs and field types (e.g. {@link #writeTag} and
+ * {@link #writeInt32}) and methods that write low-level values (e.g.
+ * {@link #writeRawVarint32} and {@link #writeRawBytes}).  If you are
+ * writing encoded protocol messages, you should use the former methods, but if
+ * you are writing some other format of your own design, use the latter.
+ *
+ * <p>This class is totally unsynchronized.
+ *
+ * @author Cyrus Najmabadi
+ */
+
+@class PBUnknownFieldSet;
+@class RingBuffer;
+@protocol PBMessage;
+
+@interface PBCodedOutputStream : NSObject {
+    NSOutputStream *output;
+    RingBuffer *buffer;
+}
+
++ (PBCodedOutputStream*) streamWithData:(NSMutableData*) data;
++ (PBCodedOutputStream*) streamWithOutputStream:(NSOutputStream*) output;
++ (PBCodedOutputStream*) streamWithOutputStream:(NSOutputStream*) output bufferSize:(SInt32) bufferSize;
+
+/**
+ * Flushes the stream and forces any buffered bytes to be written.  This
+ * does not flush the underlying NSOutputStream. Returns free space in buffer.
+ */
+- (void) flush;
+
+/** Write a single byte. */
+- (void) writeRawByte:(uint8_t) value;
+
+/** Encode and write a tag. */
+- (void) writeTag:(SInt32) fieldNumber format:(SInt32) format;
+
+/** Write a little-endian 32-bit integer. */
+- (void) writeRawLittleEndian32:(SInt32) value;
+/** Write a little-endian 64-bit integer. */
+- (void) writeRawLittleEndian64:(SInt64) value;
+
+/**
+ * Encode and write a varint.  {@code value} is treated as
+ * unsigned, so it won't be sign-extended if negative.
+ */
+- (void) writeRawVarint32:(SInt32) value;
+/** Encode and write a varint. */
+- (void) writeRawVarint64:(SInt64) value;
+
+//- (void) writeRawLittleEndian32:(SInt32) value;
+//- (void) writeRawLittleEndian64:(SInt64) value;
+
+/** Write an array of bytes. */
+- (void) writeRawData:(const NSData*) data;
+- (void) writeRawData:(const NSData*) data offset:(SInt32) offset length:(SInt32) length;
+
+- (void) writeData:(SInt32) fieldNumber value:(const NSData*) value;
+
+- (void) writeDouble:(SInt32) fieldNumber value:(Float64) value;
+- (void) writeFloat:(SInt32) fieldNumber value:(Float32) value;
+- (void) writeUInt64:(SInt32) fieldNumber value:(SInt64) value;
+- (void) writeInt64:(SInt32) fieldNumber value:(SInt64) value;
+- (void) writeInt32:(SInt32) fieldNumber value:(SInt32) value;
+- (void) writeFixed64:(SInt32) fieldNumber value:(SInt64) value;
+- (void) writeFixed32:(SInt32) fieldNumber value:(SInt32) value;
+- (void) writeBool:(SInt32) fieldNumber value:(BOOL) value;
+- (void) writeString:(SInt32) fieldNumber value:(const NSString*) value;
+- (void) writeGroup:(SInt32) fieldNumber value:(const id<PBMessage>) value;
+- (void) writeUnknownGroup:(SInt32) fieldNumber value:(const PBUnknownFieldSet*) value;
+- (void) writeMessage:(SInt32) fieldNumber value:(const id<PBMessage>) value;
+- (void) writeUInt32:(SInt32) fieldNumber value:(SInt32) value;
+- (void) writeSFixed32:(SInt32) fieldNumber value:(SInt32) value;
+- (void) writeSFixed64:(SInt32) fieldNumber value:(SInt64) value;
+- (void) writeSInt32:(SInt32) fieldNumber value:(SInt32) value;
+- (void) writeSInt64:(SInt32) fieldNumber value:(SInt64) value;
+
+- (void) writeDoubleNoTag:(Float64) value;
+- (void) writeFloatNoTag:(Float32) value;
+- (void) writeUInt64NoTag:(SInt64) value;
+- (void) writeInt64NoTag:(SInt64) value;
+- (void) writeInt32NoTag:(SInt32) value;
+- (void) writeFixed64NoTag:(SInt64) value;
+- (void) writeFixed32NoTag:(SInt32) value;
+- (void) writeBoolNoTag:(BOOL) value;
+- (void) writeStringNoTag:(const NSString*) value;
+- (void) writeGroupNoTag:(SInt32) fieldNumber value:(const id<PBMessage>) value;
+- (void) writeUnknownGroupNoTag:(SInt32) fieldNumber value:(const PBUnknownFieldSet*) value;
+- (void) writeMessageNoTag:(const id<PBMessage>) value;
+- (void) writeDataNoTag:(const NSData*) value;
+- (void) writeUInt32NoTag:(SInt32) value;
+- (void) writeEnumNoTag:(SInt32) value;
+- (void) writeSFixed32NoTag:(SInt32) value;
+- (void) writeSFixed64NoTag:(SInt64) value;
+- (void) writeSInt32NoTag:(SInt32) value;
+- (void) writeSInt64NoTag:(SInt64) value;
+
+
+/**
+ * Write a MessageSet extension field to the stream.  For historical reasons,
+ * the wire format differs from normal fields.
+ */
+- (void) writeMessageSetExtension:(SInt32) fieldNumber value:(const id<PBMessage>) value;
+
+/**
+ * Write an unparsed MessageSet extension field to the stream.  For
+ * historical reasons, the wire format differs from normal fields.
+ */
+- (void) writeRawMessageSetExtension:(SInt32) fieldNumber value:(const NSData*) value;
+
+/**
+ * Write an enum field, including tag, to the stream.  Caller is responsible
+ * for converting the enum value to its numeric value.
+ */
+- (void) writeEnum:(SInt32) fieldNumber value:(SInt32) value;
+
+@end
diff --git a/src/runtime/Classes/CodedOutputStream.m b/src/runtime/Classes/CodedOutputStream.m
new file mode 100755
index 0000000..2682ebc
--- /dev/null
+++ b/src/runtime/Classes/CodedOutputStream.m
@@ -0,0 +1,402 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "CodedOutputStream.h"
+#import "RingBuffer.h"
+#import "Message.h"
+#import "Utilities.h"
+#import "WireFormat.h"
+#import "UnknownFieldSetBuilder.h"
+#import "UnknownFieldSet.h"
+
+
+@implementation PBCodedOutputStream
+
+const SInt32 DEFAULT_BUFFER_SIZE = 4 * 1024;
+
+
+- (id)initWithOutputStream:(NSOutputStream*)_output data:(NSMutableData*)data {
+	if ( (self = [super init]) ) {
+		output = _output;
+		buffer = [[RingBuffer alloc] initWithData:data];
+	}
+	return self;
+}
+
++ (PBCodedOutputStream*)streamWithOutputStream:(NSOutputStream*)output bufferSize:(SInt32)bufferSize {
+	NSMutableData *data = [NSMutableData dataWithLength:bufferSize];
+	return [[PBCodedOutputStream alloc] initWithOutputStream:output data:data];
+}
+
+
++ (PBCodedOutputStream*)streamWithOutputStream:(NSOutputStream*)output {
+	return [PBCodedOutputStream streamWithOutputStream:output bufferSize:DEFAULT_BUFFER_SIZE];
+}
+
+
++ (PBCodedOutputStream*)streamWithData:(NSMutableData*)data {
+	return [[PBCodedOutputStream alloc] initWithOutputStream:nil data:data];
+}
+
+
+- (void)flush {
+	if (output == nil) {
+		// We're writing to a single buffer.
+		@throw [NSException exceptionWithName:@"OutOfSpace" reason:@"" userInfo:nil];
+	}
+	
+	[buffer flushToOutputStream:output];
+}
+
+
+- (void)writeRawByte:(uint8_t)value {
+	while (![buffer appendByte:value]) {
+        [self flush];
+	}
+}
+
+
+- (void)writeRawData:(const NSData*)data {
+	[self writeRawData:data offset:0 length:(SInt32)data.length];
+}
+
+
+- (void)writeRawData:(const NSData*)value offset:(SInt32)offset length:(SInt32)length {
+	while (length > 0) {
+		SInt32 written = [buffer appendData:value offset:offset length:length];
+		offset += written;
+		length -= written;
+		if (!written || length > 0) {
+            [self flush];
+		}
+	}
+}
+
+
+- (void)writeDoubleNoTag:(Float64)value {
+	[self writeRawLittleEndian64:convertFloat64ToInt64(value)];
+}
+
+
+/** Write a {@code double} field, including tag, to the stream. */
+- (void)writeDouble:(SInt32)fieldNumber value:(Float64)value {
+	[self writeTag:fieldNumber format:PBWireFormatFixed64];
+	[self writeDoubleNoTag:value];
+}
+
+
+- (void)writeFloatNoTag:(Float32)value {
+	[self writeRawLittleEndian32:convertFloat32ToInt32(value)];
+}
+
+
+/** Write a {@code float} field, including tag, to the stream. */
+- (void)writeFloat:(SInt32)fieldNumber value:(Float32)value {
+	[self writeTag:fieldNumber format:PBWireFormatFixed32];
+	[self writeFloatNoTag:value];
+}
+
+
+- (void)writeUInt64NoTag:(SInt64)value {
+	[self writeRawVarint64:value];
+}
+
+
+/** Write a {@code uint64} field, including tag, to the stream. */
+- (void)writeUInt64:(SInt32)fieldNumber value:(SInt64)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeUInt64NoTag:value];
+}
+
+
+- (void)writeInt64NoTag:(SInt64)value {
+	[self writeRawVarint64:value];
+}
+
+
+/** Write an {@code int64} field, including tag, to the stream. */
+- (void)writeInt64:(SInt32)fieldNumber value:(SInt64)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeInt64NoTag:value];
+}
+
+
+- (void)writeInt32NoTag:(SInt32)value {
+	if (value >= 0) {
+		[self writeRawVarint32:value];
+	} else {
+		// Must sign-extend
+		[self writeRawVarint64:value];
+	}
+}
+
+
+/** Write an {@code int32} field, including tag, to the stream. */
+- (void)writeInt32:(SInt32)fieldNumber value:(SInt32)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeInt32NoTag:value];
+}
+
+
+- (void)writeFixed64NoTag:(SInt64)value {
+	[self writeRawLittleEndian64:value];
+}
+
+
+/** Write a {@code fixed64} field, including tag, to the stream. */
+- (void)writeFixed64:(SInt32)fieldNumber value:(SInt64)value {
+	[self writeTag:fieldNumber format:PBWireFormatFixed64];
+	[self writeFixed64NoTag:value];
+}
+
+
+- (void)writeFixed32NoTag:(SInt32)value {
+	[self writeRawLittleEndian32:value];
+}
+
+
+/** Write a {@code fixed32} field, including tag, to the stream. */
+- (void)writeFixed32:(SInt32)fieldNumber value:(SInt32)value {
+	[self writeTag:fieldNumber format:PBWireFormatFixed32];
+	[self writeFixed32NoTag:value];
+}
+
+
+- (void)writeBoolNoTag:(BOOL)value {
+	[self writeRawByte:(value ? 1 : 0)];
+}
+
+
+/** Write a {@code bool} field, including tag, to the stream. */
+- (void)writeBool:(SInt32)fieldNumber value:(BOOL)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeBoolNoTag:value];
+}
+
+
+- (void)writeStringNoTag:(const NSString*)value {
+	NSData* data = [value dataUsingEncoding:NSUTF8StringEncoding];
+	[self writeRawVarint32:(SInt32)data.length];
+	[self writeRawData:data];
+}
+
+
+/** Write a {@code string} field, including tag, to the stream. */
+- (void)writeString:(SInt32)fieldNumber value:(const NSString*)value {
+	[self writeTag:fieldNumber format:PBWireFormatLengthDelimited];
+	[self writeStringNoTag:value];
+}
+
+
+- (void)writeGroupNoTag:(SInt32)fieldNumber value:(const id<PBMessage>)value {
+	[value writeToCodedOutputStream:self];
+	[self writeTag:fieldNumber format:PBWireFormatEndGroup];
+}
+
+
+/** Write a {@code group} field, including tag, to the stream. */
+- (void)writeGroup:(SInt32)fieldNumber value:(const id<PBMessage>)value {
+	[self writeTag:fieldNumber format:PBWireFormatStartGroup];
+	[self writeGroupNoTag:fieldNumber value:value];
+}
+
+
+- (void)writeUnknownGroupNoTag:(SInt32)fieldNumber value:(const PBUnknownFieldSet*)value {
+	[value writeToCodedOutputStream:self];
+	[self writeTag:fieldNumber format:PBWireFormatEndGroup];
+}
+
+
+/** Write a group represented by an {@link PBUnknownFieldSet}. */
+- (void)writeUnknownGroup:(SInt32)fieldNumber value:(const PBUnknownFieldSet*)value {
+	[self writeTag:fieldNumber format:PBWireFormatStartGroup];
+	[self writeUnknownGroupNoTag:fieldNumber value:value];
+}
+
+
+- (void)writeMessageNoTag:(const id<PBMessage>)value {
+	[self writeRawVarint32:[value serializedSize]];
+	[value writeToCodedOutputStream:self];
+}
+
+
+/** Write an embedded message field, including tag, to the stream. */
+- (void)writeMessage:(SInt32)fieldNumber value:(const id<PBMessage>)value {
+	[self writeTag:fieldNumber format:PBWireFormatLengthDelimited];
+	[self writeMessageNoTag:value];
+}
+
+
+- (void)writeDataNoTag:(const NSData*)value {
+	[self writeRawVarint32:(SInt32)value.length];
+	[self writeRawData:value];
+}
+
+
+/** Write a {@code bytes} field, including tag, to the stream. */
+- (void)writeData:(SInt32)fieldNumber value:(const NSData*)value {
+	[self writeTag:fieldNumber format:PBWireFormatLengthDelimited];
+	[self writeDataNoTag:value];
+}
+
+
+- (void)writeUInt32NoTag:(SInt32)value {
+	[self writeRawVarint32:value];
+}
+
+
+/** Write a {@code uint32} field, including tag, to the stream. */
+- (void)writeUInt32:(SInt32)fieldNumber value:(SInt32)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeUInt32NoTag:value];
+}
+
+
+- (void)writeEnumNoTag:(SInt32)value {
+	[self writeRawVarint32:value];
+}
+
+
+- (void)writeEnum:(SInt32)fieldNumber value:(SInt32)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeEnumNoTag:value];
+}
+
+
+- (void)writeSFixed32NoTag:(SInt32)value {
+	[self writeRawLittleEndian32:value];
+}
+
+
+/** Write an {@code sfixed32} field, including tag, to the stream. */
+- (void)writeSFixed32:(SInt32)fieldNumber value:(SInt32)value {
+	[self writeTag:fieldNumber format:PBWireFormatFixed32];
+	[self writeSFixed32NoTag:value];
+}
+
+
+- (void)writeSFixed64NoTag:(SInt64)value {
+	[self writeRawLittleEndian64:value];
+}
+
+
+/** Write an {@code sfixed64} field, including tag, to the stream. */
+- (void)writeSFixed64:(SInt32)fieldNumber value:(SInt64)value {
+	[self writeTag:fieldNumber format:PBWireFormatFixed64];
+	[self writeSFixed64NoTag:value];
+}
+
+
+- (void)writeSInt32NoTag:(SInt32)value {
+	[self writeRawVarint32:encodeZigZag32(value)];
+}
+
+
+/** Write an {@code sint32} field, including tag, to the stream. */
+- (void)writeSInt32:(SInt32)fieldNumber value:(SInt32)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeSInt32NoTag:value];
+}
+
+
+- (void)writeSInt64NoTag:(SInt64)value {
+	[self writeRawVarint64:encodeZigZag64(value)];
+}
+
+
+/** Write an {@code sint64} field, including tag, to the stream. */
+- (void)writeSInt64:(SInt32)fieldNumber value:(SInt64)value {
+	[self writeTag:fieldNumber format:PBWireFormatVarint];
+	[self writeSInt64NoTag:value];
+}
+
+
+/**
+ * Write a MessageSet extension field to the stream.  For historical reasons,
+ * the wire format differs from normal fields.
+ */
+- (void)writeMessageSetExtension:(SInt32)fieldNumber value:(const id<PBMessage>)value {
+	[self writeTag:PBWireFormatMessageSetItem format:PBWireFormatStartGroup];
+	[self writeUInt32:PBWireFormatMessageSetTypeId value:fieldNumber];
+	[self writeMessage:PBWireFormatMessageSetMessage value:value];
+	[self writeTag:PBWireFormatMessageSetItem format:PBWireFormatEndGroup];
+}
+
+
+/**
+ * Write an unparsed MessageSet extension field to the stream.  For
+ * historical reasons, the wire format differs from normal fields.
+ */
+- (void)writeRawMessageSetExtension:(SInt32)fieldNumber value:(const NSData*)value {
+	[self writeTag:PBWireFormatMessageSetItem format:PBWireFormatStartGroup];
+	[self writeUInt32:PBWireFormatMessageSetTypeId value:fieldNumber];
+	[self writeData:PBWireFormatMessageSetMessage value:value];
+	[self writeTag:PBWireFormatMessageSetItem format:PBWireFormatEndGroup];
+}
+
+
+- (void)writeTag:(SInt32)fieldNumber format:(SInt32)format {
+	[self writeRawVarint32:PBWireFormatMakeTag(fieldNumber, format)];
+}
+
+
+- (void)writeRawVarint32:(SInt32)value {
+	while (YES) {
+		if ((value & ~0x7F) == 0) {
+			[self writeRawByte:value];
+			return;
+		} else {
+			[self writeRawByte:((value & 0x7F) | 0x80)];
+			value = logicalRightShift32(value, 7);
+		}
+	}
+}
+
+
+- (void)writeRawVarint64:(SInt64)value {
+	while (YES) {
+		if ((value & ~0x7FL) == 0) {
+			[self writeRawByte:((SInt32)value)];
+			return;
+		} else {
+			[self writeRawByte:(((SInt32)value & 0x7F) | 0x80)];
+			value = logicalRightShift64(value, 7);
+		}
+	}
+}
+
+
+- (void)writeRawLittleEndian32:(SInt32)value {
+	[self writeRawByte:((value      ) & 0xFF)];
+	[self writeRawByte:((value >>  8) & 0xFF)];
+	[self writeRawByte:((value >> 16) & 0xFF)];
+	[self writeRawByte:((value >> 24) & 0xFF)];
+}
+
+
+- (void)writeRawLittleEndian64:(SInt64)value {
+	[self writeRawByte:((SInt32)(value      ) & 0xFF)];
+	[self writeRawByte:((SInt32)(value >>  8) & 0xFF)];
+	[self writeRawByte:((SInt32)(value >> 16) & 0xFF)];
+	[self writeRawByte:((SInt32)(value >> 24) & 0xFF)];
+	[self writeRawByte:((SInt32)(value >> 32) & 0xFF)];
+	[self writeRawByte:((SInt32)(value >> 40) & 0xFF)];
+	[self writeRawByte:((SInt32)(value >> 48) & 0xFF)];
+	[self writeRawByte:((SInt32)(value >> 56) & 0xFF)];
+}
+
+@end
diff --git a/src/runtime/Classes/ConcreteExtensionField.h b/src/runtime/Classes/ConcreteExtensionField.h
new file mode 100755
index 0000000..7524d46
--- /dev/null
+++ b/src/runtime/Classes/ConcreteExtensionField.h
@@ -0,0 +1,65 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "ExtensionField.h"
+
+typedef enum {
+  PBExtensionTypeBool,
+  PBExtensionTypeFixed32,
+  PBExtensionTypeSFixed32,
+  PBExtensionTypeFloat,
+  PBExtensionTypeFixed64,
+  PBExtensionTypeSFixed64,
+  PBExtensionTypeDouble,
+  PBExtensionTypeInt32,
+  PBExtensionTypeInt64,
+  PBExtensionTypeSInt32,
+  PBExtensionTypeSInt64,
+  PBExtensionTypeUInt32,
+  PBExtensionTypeUInt64,
+  PBExtensionTypeBytes,
+  PBExtensionTypeString,
+  PBExtensionTypeMessage,
+  PBExtensionTypeGroup,
+  PBExtensionTypeEnum
+} PBExtensionType;
+
+@interface PBConcreteExtensionField : NSObject<PBExtensionField> {
+@private
+  PBExtensionType type;
+
+  Class extendedClass;
+  SInt32 fieldNumber;
+  id defaultValue;
+
+  Class messageOrGroupClass;
+
+  BOOL isRepeated;
+  BOOL isPacked;
+  BOOL isMessageSetWireFormat;
+}
+
++ (PBConcreteExtensionField*) extensionWithType:(PBExtensionType) type
+                                extendedClass:(Class) extendedClass
+                                  fieldNumber:(SInt32) fieldNumber
+                                 defaultValue:(id) defaultValue
+                            messageOrGroupClass:(Class) messageOrGroupClass
+                                   isRepeated:(BOOL) isRepeated
+                                     isPacked:(BOOL) isPacked
+                       isMessageSetWireFormat:(BOOL) isMessageSetWireFormat;
+
+@end
diff --git a/src/runtime/Classes/ConcreteExtensionField.m b/src/runtime/Classes/ConcreteExtensionField.m
new file mode 100755
index 0000000..d7567c4
--- /dev/null
+++ b/src/runtime/Classes/ConcreteExtensionField.m
@@ -0,0 +1,582 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "ConcreteExtensionField.h"
+
+#import "AbstractMessage.h"
+#import "CodedInputStream.h"
+#import "CodedOutputStream.h"
+#import "ExtendableMessageBuilder.h"
+#import "MessageBuilder.h"
+#import "Utilities.h"
+#import "WireFormat.h"
+
+@interface PBConcreteExtensionField()
+@property PBExtensionType type;
+@property (assign) Class extendedClass;
+@property SInt32 fieldNumber;
+@property (strong) id defaultValue;
+@property (assign) Class messageOrGroupClass;
+@property BOOL isRepeated;
+@property BOOL isPacked;
+@property BOOL isMessageSetWireFormat;
+@end
+
+@implementation PBConcreteExtensionField
+
+@synthesize type;
+@synthesize extendedClass;
+@synthesize fieldNumber;
+@synthesize defaultValue;
+@synthesize messageOrGroupClass;
+@synthesize isRepeated;
+@synthesize isPacked;
+@synthesize isMessageSetWireFormat;
+
+
+
+- (id)     initWithType:(PBExtensionType) type_
+          extendedClass:(Class) extendedClass_
+            fieldNumber:(SInt32) fieldNumber_
+           defaultValue:(id) defaultValue_
+    messageOrGroupClass:(Class) messageOrGroupClass_
+             isRepeated:(BOOL) isRepeated_
+               isPacked:(BOOL) isPacked_
+    isMessageSetWireFormat:(BOOL) isMessageSetWireFormat_ {
+  if ((self = [super init])) {
+    self.type = type_;
+    self.extendedClass = extendedClass_;
+    self.fieldNumber = fieldNumber_;
+    self.defaultValue = defaultValue_;
+    self.messageOrGroupClass = messageOrGroupClass_;
+    self.isRepeated = isRepeated_;
+    self.isPacked = isPacked_;
+    self.isMessageSetWireFormat = isMessageSetWireFormat_;
+  }
+
+  return self;
+}
+
+
++ (PBConcreteExtensionField*) extensionWithType:(PBExtensionType) type
+                                extendedClass:(Class) extendedClass
+                                  fieldNumber:(SInt32) fieldNumber
+                                 defaultValue:(id) defaultValue
+                    messageOrGroupClass:(Class) messageOrGroupClass
+                                   isRepeated:(BOOL) isRepeated
+                                     isPacked:(BOOL) isPacked
+                       isMessageSetWireFormat:(BOOL) isMessageSetWireFormat {
+  return [[PBConcreteExtensionField alloc] initWithType:type
+                                         extendedClass:extendedClass
+                                           fieldNumber:fieldNumber
+                                          defaultValue:defaultValue
+                             messageOrGroupClass:messageOrGroupClass
+                                            isRepeated:isRepeated
+                                              isPacked:isPacked
+                                 isMessageSetWireFormat:isMessageSetWireFormat];
+}
+
+
+- (PBWireFormat) wireType {
+  if (isPacked) {
+    return PBWireFormatLengthDelimited;
+  }
+
+  switch (type) {
+    case PBExtensionTypeBool:     return PBWireFormatVarint;
+    case PBExtensionTypeFixed32:  return PBWireFormatFixed32;
+    case PBExtensionTypeSFixed32: return PBWireFormatFixed32;
+    case PBExtensionTypeFloat:    return PBWireFormatFixed32;
+    case PBExtensionTypeFixed64:  return PBWireFormatFixed64;
+    case PBExtensionTypeSFixed64: return PBWireFormatFixed64;
+    case PBExtensionTypeDouble:   return PBWireFormatFixed64;
+    case PBExtensionTypeInt32:    return PBWireFormatVarint;
+    case PBExtensionTypeInt64:    return PBWireFormatVarint;
+    case PBExtensionTypeSInt32:   return PBWireFormatVarint;
+    case PBExtensionTypeSInt64:   return PBWireFormatVarint;
+    case PBExtensionTypeUInt32:   return PBWireFormatVarint;
+    case PBExtensionTypeUInt64:   return PBWireFormatVarint;
+    case PBExtensionTypeBytes:    return PBWireFormatLengthDelimited;
+    case PBExtensionTypeString:   return PBWireFormatLengthDelimited;
+    case PBExtensionTypeMessage:  return PBWireFormatLengthDelimited;
+    case PBExtensionTypeGroup:    return PBWireFormatStartGroup;
+    case PBExtensionTypeEnum:     return PBWireFormatVarint;
+  }
+
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+BOOL typeIsFixedSize(PBExtensionType type) {
+  switch (type) {
+    case PBExtensionTypeBool:
+    case PBExtensionTypeFixed32:
+    case PBExtensionTypeSFixed32:
+    case PBExtensionTypeFloat:
+    case PBExtensionTypeFixed64:
+    case PBExtensionTypeSFixed64:
+    case PBExtensionTypeDouble:
+      return YES;
+    default:
+      return NO;
+  }
+}
+
+
+SInt32 typeSize(PBExtensionType type) {
+  switch (type) {
+    case PBExtensionTypeBool:
+      return 1;
+    case PBExtensionTypeFixed32:
+    case PBExtensionTypeSFixed32:
+    case PBExtensionTypeFloat:
+      return 4;
+    case PBExtensionTypeFixed64:
+    case PBExtensionTypeSFixed64:
+    case PBExtensionTypeDouble:
+      return 8;
+    default:
+      break;
+  }
+
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+- (void)           writeSingleValue:(id) value
+    includingTagToCodedOutputStream:(PBCodedOutputStream*) output {
+  switch (type) {
+    case PBExtensionTypeBool:
+      [output writeBool:fieldNumber value:[value boolValue]];
+      return;
+    case PBExtensionTypeFixed32:
+      [output writeFixed32:fieldNumber value:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeSFixed32:
+      [output writeSFixed32:fieldNumber value:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeFloat:
+      [output writeFloat:fieldNumber value:[value floatValue]];
+      return;
+    case PBExtensionTypeFixed64:
+      [output writeFixed64:fieldNumber value:[value longLongValue]];
+      return;
+    case PBExtensionTypeSFixed64:
+      [output writeSFixed64:fieldNumber value:[value longLongValue]];
+      return;
+    case PBExtensionTypeDouble:
+      [output writeDouble:fieldNumber value:[value doubleValue]];
+      return;
+    case PBExtensionTypeInt32:
+      [output writeInt32:fieldNumber value:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeInt64:
+      [output writeInt64:fieldNumber value:[value longLongValue]];
+      return;
+    case PBExtensionTypeSInt32:
+      [output writeSInt32:fieldNumber value:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeSInt64:
+      [output writeSInt64:fieldNumber value:[value longLongValue]];
+      return;
+    case PBExtensionTypeUInt32:
+      [output writeUInt32:fieldNumber value:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeUInt64:
+      [output writeUInt64:fieldNumber value:[value longLongValue]];
+      return;
+    case PBExtensionTypeBytes:
+      [output writeData:fieldNumber value:value];
+      return;
+    case PBExtensionTypeString:
+      [output writeString:fieldNumber value:value];
+      return;
+    case PBExtensionTypeGroup:
+      [output writeGroup:fieldNumber value:value];
+      return;
+    case PBExtensionTypeEnum:
+      [output writeEnum:fieldNumber value:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeMessage:
+      if (isMessageSetWireFormat) {
+        [output writeMessageSetExtension:fieldNumber value:value];
+      } else {
+        [output writeMessage:fieldNumber value:value];
+      }
+      return;
+  }
+
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+- (void)           writeSingleValue:(id) value
+    noTagToCodedOutputStream:(PBCodedOutputStream*) output {
+  switch (type) {
+    case PBExtensionTypeBool:
+      [output writeBoolNoTag:[value boolValue]];
+      return;
+    case PBExtensionTypeFixed32:
+      [output writeFixed32NoTag:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeSFixed32:
+      [output writeSFixed32NoTag:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeFloat:
+      [output writeFloatNoTag:[value floatValue]];
+      return;
+    case PBExtensionTypeFixed64:
+      [output writeFixed64NoTag:[value longLongValue]];
+      return;
+    case PBExtensionTypeSFixed64:
+      [output writeSFixed64NoTag:[value longLongValue]];
+      return;
+    case PBExtensionTypeDouble:
+      [output writeDoubleNoTag:[value doubleValue]];
+      return;
+    case PBExtensionTypeInt32:
+      [output writeInt32NoTag:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeInt64:
+      [output writeInt64NoTag:[value longLongValue]];
+      return;
+    case PBExtensionTypeSInt32:
+      [output writeSInt32NoTag:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeSInt64:
+      [output writeSInt64NoTag:[value longLongValue]];
+      return;
+    case PBExtensionTypeUInt32:
+      [output writeUInt32NoTag:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeUInt64:
+      [output writeUInt64NoTag:[value longLongValue]];
+      return;
+    case PBExtensionTypeBytes:
+      [output writeDataNoTag:value];
+      return;
+    case PBExtensionTypeString:
+      [output writeStringNoTag:value];
+      return;
+    case PBExtensionTypeGroup:
+      [output writeGroupNoTag:fieldNumber value:value];
+      return;
+    case PBExtensionTypeEnum:
+      [output writeEnumNoTag:(SInt32)[value integerValue]];
+      return;
+    case PBExtensionTypeMessage:
+      [output writeMessageNoTag:value];
+      return;
+  }
+
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+- (SInt32) computeSingleSerializedSizeNoTag:(id) value {
+  switch (type) {
+    case PBExtensionTypeBool:     return computeBoolSizeNoTag([value boolValue]);
+    case PBExtensionTypeFixed32:  return computeFixed32SizeNoTag((SInt32)[value integerValue]);
+    case PBExtensionTypeSFixed32: return computeSFixed32SizeNoTag((SInt32)[value integerValue]);
+    case PBExtensionTypeFloat:    return computeFloatSizeNoTag([value floatValue]);
+    case PBExtensionTypeFixed64:  return computeFixed64SizeNoTag([value longLongValue]);
+    case PBExtensionTypeSFixed64: return computeSFixed64SizeNoTag([value longLongValue]);
+    case PBExtensionTypeDouble:   return computeDoubleSizeNoTag([value doubleValue]);
+    case PBExtensionTypeInt32:    return computeInt32SizeNoTag((SInt32)[value integerValue]);
+    case PBExtensionTypeInt64:    return computeInt64SizeNoTag([value longLongValue]);
+    case PBExtensionTypeSInt32:   return computeSInt32SizeNoTag((SInt32)[value integerValue]);
+    case PBExtensionTypeSInt64:   return computeSInt64SizeNoTag([value longLongValue]);
+    case PBExtensionTypeUInt32:   return computeUInt32SizeNoTag((SInt32)[value integerValue]);
+    case PBExtensionTypeUInt64:   return computeUInt64SizeNoTag([value longLongValue]);
+    case PBExtensionTypeBytes:    return computeDataSizeNoTag(value);
+    case PBExtensionTypeString:   return computeStringSizeNoTag(value);
+    case PBExtensionTypeGroup:    return computeGroupSizeNoTag(value);
+    case PBExtensionTypeEnum:     return computeEnumSizeNoTag((SInt32)[value integerValue]);
+    case PBExtensionTypeMessage:  return computeMessageSizeNoTag(value);
+  }
+
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+- (SInt32) computeSingleSerializedSizeIncludingTag:(id) value {
+  switch (type) {
+    case PBExtensionTypeBool:     return computeBoolSize(fieldNumber, [value boolValue]);
+    case PBExtensionTypeFixed32:  return computeFixed32Size(fieldNumber,(SInt32) [value integerValue]);
+    case PBExtensionTypeSFixed32: return computeSFixed32Size(fieldNumber, (SInt32)[value integerValue]);
+    case PBExtensionTypeFloat:    return computeFloatSize(fieldNumber, [value floatValue]);
+    case PBExtensionTypeFixed64:  return computeFixed64Size(fieldNumber, [value longLongValue]);
+    case PBExtensionTypeSFixed64: return computeSFixed64Size(fieldNumber, [value longLongValue]);
+    case PBExtensionTypeDouble:   return computeDoubleSize(fieldNumber, [value doubleValue]);
+    case PBExtensionTypeInt32:    return computeInt32Size(fieldNumber, (SInt32)[value integerValue]);
+    case PBExtensionTypeInt64:    return computeInt64Size(fieldNumber, [value longLongValue]);
+    case PBExtensionTypeSInt32:   return computeSInt32Size(fieldNumber, (SInt32)[value integerValue]);
+    case PBExtensionTypeSInt64:   return computeSInt64Size(fieldNumber, [value longLongValue]);
+    case PBExtensionTypeUInt32:   return computeUInt32Size(fieldNumber, (SInt32)[value integerValue]);
+    case PBExtensionTypeUInt64:   return computeUInt64Size(fieldNumber, [value longLongValue]);
+    case PBExtensionTypeBytes:    return computeDataSize(fieldNumber, value);
+    case PBExtensionTypeString:   return computeStringSize(fieldNumber, value);
+    case PBExtensionTypeGroup:    return computeGroupSize(fieldNumber, value);
+    case PBExtensionTypeEnum:     return computeEnumSize(fieldNumber, (SInt32)[value integerValue]);
+    case PBExtensionTypeMessage:
+      if (isMessageSetWireFormat) {
+        return computeMessageSetExtensionSize(fieldNumber, value);
+      } else {
+        return computeMessageSize(fieldNumber, value);
+      }
+  }
+
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+- (void) writeDescriptionOfSingleValue:(id) value
+                                    to:(NSMutableString*) output
+                            withIndent:(NSString*) indent {
+  switch (type) {
+    case PBExtensionTypeBool:
+    case PBExtensionTypeFixed32:
+    case PBExtensionTypeSFixed32:
+    case PBExtensionTypeFloat:
+    case PBExtensionTypeFixed64:
+    case PBExtensionTypeSFixed64:
+    case PBExtensionTypeDouble:
+    case PBExtensionTypeInt32:
+    case PBExtensionTypeInt64:
+    case PBExtensionTypeSInt32:
+    case PBExtensionTypeSInt64:
+    case PBExtensionTypeUInt32:
+    case PBExtensionTypeUInt64:
+    case PBExtensionTypeBytes:
+    case PBExtensionTypeString:
+    case PBExtensionTypeEnum:
+      [output appendFormat:@"%@%@\n", indent, value];
+      return;
+    case PBExtensionTypeGroup:
+    case PBExtensionTypeMessage:
+      [((PBAbstractMessage *)value) writeDescriptionTo:output withIndent:indent];
+      return;
+  }
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+- (void)writeRepeatedValues:(NSArray*) values includingTagsToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (isPacked) {
+    [output writeTag:fieldNumber format:PBWireFormatLengthDelimited];
+    SInt32 dataSize = 0;
+    if (typeIsFixedSize(type)) {
+      dataSize = (SInt32)(values.count * typeSize(type));
+    } else {
+      for (id value in values) {
+        dataSize += [self computeSingleSerializedSizeNoTag:value];
+      }
+    }
+    [output writeRawVarint32:dataSize];
+    for (id value in values) {
+      [self writeSingleValue:value noTagToCodedOutputStream:output];
+    }
+  } else {
+    for (id value in values) {
+      [self writeSingleValue:value includingTagToCodedOutputStream:output];
+    }
+  }
+}
+
+
+- (void) writeValue:(id) value includingTagToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (isRepeated) {
+    [self writeRepeatedValues:value includingTagsToCodedOutputStream:output];
+  } else {
+    [self writeSingleValue:value includingTagToCodedOutputStream:output];
+  }
+}
+
+
+- (SInt32) computeRepeatedSerializedSizeIncludingTags:(NSArray*) values {
+  if (isPacked) {
+    SInt32 size = 0;
+    if (typeIsFixedSize(type)) {
+      size = (SInt32)(values.count * typeSize(type));
+    } else {
+      for (id value in values) {
+        size += [self computeSingleSerializedSizeNoTag:value];
+      }
+    }
+    return size + computeTagSize(fieldNumber) + computeRawVarint32Size(size);
+  } else {
+    SInt32 size = 0;
+    for (id value in values) {
+      size += [self computeSingleSerializedSizeIncludingTag:value];
+    }
+    return size;
+  }
+}
+
+
+- (SInt32) computeSerializedSizeIncludingTag:(id) value {
+  if (isRepeated) {
+    return [self computeRepeatedSerializedSizeIncludingTags:value];
+  } else {
+    return [self computeSingleSerializedSizeIncludingTag:value];
+  }
+}
+
+
+- (void) writeDescriptionOf:(id)value
+                         to:(NSMutableString *)output
+                 withIndent:(NSString *)indent {
+  if (isRepeated) {
+    NSArray* values = value;
+    for (id singleValue in values) {
+      [self writeDescriptionOfSingleValue:singleValue to:output withIndent:indent];
+    }
+  } else {
+    [self writeDescriptionOfSingleValue:value to:output withIndent:indent];
+  }
+}
+
+- (void) mergeMessageSetExtentionFromCodedInputStream:(PBCodedInputStream*) input
+                                        unknownFields:(PBUnknownFieldSetBuilder*) unknownFields {
+  @throw [NSException exceptionWithName:@"NYI" reason:@"" userInfo:nil];
+
+  // The wire format for MessageSet is:
+  //   message MessageSet {
+  //     repeated group Item = 1 {
+  //       required int32 typeId = 2;
+  //       required bytes message = 3;
+  //     }
+  //   }
+  // "typeId" is the extension's field number.  The extension can only be
+  // a message type, where "message" contains the encoded bytes of that
+  // message.
+  //
+  // In practice, we will probably never see a MessageSet item in which
+  // the message appears before the type ID, or where either field does not
+  // appear exactly once.  However, in theory such cases are valid, so we
+  // should be prepared to accept them.
+
+  //int typeId = 0;
+//  ByteString rawBytes = null;
+//
+//  while (true) {
+//    final int tag = input.readTag();
+//    if (tag == 0) {
+//      break;
+//    }
+//
+//    if (tag == WireFormat.MESSAGE_SET_TYPE_ID_TAG) {
+//      typeId = input.readUInt32();
+//      // Zero is not a valid type ID.
+//      if (typeId != 0) {
+//        if (rawBytes != null) {
+//          unknownFields.mergeField(typeId,
+//                                   UnknownFieldSet.Field.newBuilder()
+//                                   .addLengthDelimited(rawBytes)
+//                                   .build());
+//          rawBytes = null;
+//        }
+//      }
+//    } else if (tag == WireFormat.MESSAGE_SET_MESSAGE_TAG) {
+//      if (typeId == 0) {
+//        // We haven't seen a type ID yet, so we have to store the raw bytes
+//        // for now.
+//        rawBytes = input.readBytes();
+//      } else {
+//        unknownFields.mergeField(typeId,
+//                                 UnknownFieldSet.Field.newBuilder()
+//                                 .addLengthDelimited(input.readBytes())
+//                                 .build());
+//      }
+//    } else {
+//      // Unknown fieldNumber.  Skip it.
+//      if (!input.skipField(tag)) {
+//        break;  // end of group
+//      }
+//    }
+//  }
+//
+//  input.checkLastTagWas(WireFormat.MESSAGE_SET_ITEM_END_TAG);
+}
+
+
+- (id) readSingleValueFromCodedInputStream:(PBCodedInputStream*) input
+                         extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  switch (type) {
+    case PBExtensionTypeBool:     return [NSNumber numberWithBool:[input readBool]];
+    case PBExtensionTypeFixed32:  return @([input readFixed32]);
+    case PBExtensionTypeSFixed32: return @([input readSFixed32]);
+    case PBExtensionTypeFloat:    return [NSNumber numberWithFloat:[input readFloat]];
+    case PBExtensionTypeFixed64:  return [NSNumber numberWithLongLong:[input readFixed64]];
+    case PBExtensionTypeSFixed64: return [NSNumber numberWithLongLong:[input readSFixed64]];
+    case PBExtensionTypeDouble:   return [NSNumber numberWithDouble:[input readDouble]];
+    case PBExtensionTypeInt32:    return @([input readInt32]);
+    case PBExtensionTypeInt64:    return [NSNumber numberWithLongLong:[input readInt64]];
+    case PBExtensionTypeSInt32:   return @([input readSInt32]);
+    case PBExtensionTypeSInt64:   return [NSNumber numberWithLongLong:[input readSInt64]];
+    case PBExtensionTypeUInt32:   return @([input readUInt32]);
+    case PBExtensionTypeUInt64:   return [NSNumber numberWithLongLong:[input readUInt64]];
+    case PBExtensionTypeBytes:    return [input readData];
+    case PBExtensionTypeString:   return [input readString];
+    case PBExtensionTypeEnum:     return @([input readEnum]);
+    case PBExtensionTypeGroup:
+    {
+      id<PBMessageBuilder> builder = [messageOrGroupClass builder];
+      [input readGroup:fieldNumber builder:builder extensionRegistry:extensionRegistry];
+      return [builder build];
+    }
+
+    case PBExtensionTypeMessage:
+    {
+      id<PBMessageBuilder> builder = [messageOrGroupClass builder];
+      [input readMessage:builder extensionRegistry:extensionRegistry];
+      return [builder build];
+    }
+  }
+
+  @throw [NSException exceptionWithName:@"InternalError" reason:@"" userInfo:nil];
+}
+
+
+- (void) mergeFromCodedInputStream:(PBCodedInputStream*) input
+                     unknownFields:(PBUnknownFieldSetBuilder*) unknownFields
+     extensionRegistry:(PBExtensionRegistry*) extensionRegistry
+    builder:(PBExtendableMessageBuilder*) builder
+                               tag:(SInt32) tag {
+  if (isPacked) {
+    SInt32 length = [input readRawVarint32];
+    SInt32 limit = [input pushLimit:length];
+    while ([input bytesUntilLimit] > 0) {
+      id value = [self readSingleValueFromCodedInputStream:input extensionRegistry:extensionRegistry];
+      [builder addExtension:self value:value];
+    }
+    [input popLimit:limit];
+  } else if (isMessageSetWireFormat) {
+    [self mergeMessageSetExtentionFromCodedInputStream:input
+                                         unknownFields:unknownFields];
+  } else {
+    id value = [self readSingleValueFromCodedInputStream:input extensionRegistry:extensionRegistry];
+    if (isRepeated) {
+      [builder addExtension:self value:value];
+    } else {
+      [builder setExtension:self value:value];
+    }
+  }
+}
+
+
+@end
diff --git a/src/runtime/Classes/Descriptor.pb.h b/src/runtime/Classes/Descriptor.pb.h
new file mode 100755
index 0000000..4567b9e
--- /dev/null
+++ b/src/runtime/Classes/Descriptor.pb.h
@@ -0,0 +1,1796 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+// @@protoc_insertion_point(imports)
+#import "ProtocolBuffers.h"
+
+@class PBDescriptorProto;
+@class PBDescriptorProtoBuilder;
+@class PBDescriptorProtoExtensionRange;
+@class PBDescriptorProtoExtensionRangeBuilder;
+@class PBEnumDescriptorProto;
+@class PBEnumDescriptorProtoBuilder;
+@class PBEnumOptions;
+@class PBEnumOptionsBuilder;
+@class PBEnumValueDescriptorProto;
+@class PBEnumValueDescriptorProtoBuilder;
+@class PBEnumValueOptions;
+@class PBEnumValueOptionsBuilder;
+@class PBFieldDescriptorProto;
+@class PBFieldDescriptorProtoBuilder;
+@class PBFieldOptions;
+@class PBFieldOptionsBuilder;
+@class PBFileDescriptorProto;
+@class PBFileDescriptorProtoBuilder;
+@class PBFileDescriptorSet;
+@class PBFileDescriptorSetBuilder;
+@class PBFileOptions;
+@class PBFileOptionsBuilder;
+@class PBMessageOptions;
+@class PBMessageOptionsBuilder;
+@class PBMethodDescriptorProto;
+@class PBMethodDescriptorProtoBuilder;
+@class PBMethodOptions;
+@class PBMethodOptionsBuilder;
+@class PBOneofDescriptorProto;
+@class PBOneofDescriptorProtoBuilder;
+@class PBServiceDescriptorProto;
+@class PBServiceDescriptorProtoBuilder;
+@class PBServiceOptions;
+@class PBServiceOptionsBuilder;
+@class PBSourceCodeInfo;
+@class PBSourceCodeInfoBuilder;
+@class PBSourceCodeInfoLocation;
+@class PBSourceCodeInfoLocationBuilder;
+@class PBUninterpretedOption;
+@class PBUninterpretedOptionBuilder;
+@class PBUninterpretedOptionNamePart;
+@class PBUninterpretedOptionNamePartBuilder;
+#ifndef __has_feature
+  #define __has_feature(x) 0 // Compatibility with non-clang compilers.
+#endif // __has_feature
+
+#ifndef NS_RETURNS_NOT_RETAINED
+  #if __has_feature(attribute_ns_returns_not_retained)
+    #define NS_RETURNS_NOT_RETAINED __attribute__((ns_returns_not_retained))
+  #else
+    #define NS_RETURNS_NOT_RETAINED
+  #endif
+#endif
+
+typedef enum {
+  PBFieldDescriptorProtoTypeTypeDouble = 1,
+  PBFieldDescriptorProtoTypeTypeFloat = 2,
+  PBFieldDescriptorProtoTypeTypeInt64 = 3,
+  PBFieldDescriptorProtoTypeTypeUint64 = 4,
+  PBFieldDescriptorProtoTypeTypeInt32 = 5,
+  PBFieldDescriptorProtoTypeTypeFixed64 = 6,
+  PBFieldDescriptorProtoTypeTypeFixed32 = 7,
+  PBFieldDescriptorProtoTypeTypeBool = 8,
+  PBFieldDescriptorProtoTypeTypeString = 9,
+  PBFieldDescriptorProtoTypeTypeGroup = 10,
+  PBFieldDescriptorProtoTypeTypeMessage = 11,
+  PBFieldDescriptorProtoTypeTypeBytes = 12,
+  PBFieldDescriptorProtoTypeTypeUint32 = 13,
+  PBFieldDescriptorProtoTypeTypeEnum = 14,
+  PBFieldDescriptorProtoTypeTypeSfixed32 = 15,
+  PBFieldDescriptorProtoTypeTypeSfixed64 = 16,
+  PBFieldDescriptorProtoTypeTypeSint32 = 17,
+  PBFieldDescriptorProtoTypeTypeSint64 = 18,
+} PBFieldDescriptorProtoType;
+
+BOOL PBFieldDescriptorProtoTypeIsValidValue(PBFieldDescriptorProtoType value);
+
+typedef enum {
+  PBFieldDescriptorProtoLabelLabelOptional = 1,
+  PBFieldDescriptorProtoLabelLabelRequired = 2,
+  PBFieldDescriptorProtoLabelLabelRepeated = 3,
+} PBFieldDescriptorProtoLabel;
+
+BOOL PBFieldDescriptorProtoLabelIsValidValue(PBFieldDescriptorProtoLabel value);
+
+typedef enum {
+  PBFileOptionsOptimizeModeSpeed = 1,
+  PBFileOptionsOptimizeModeCodeSize = 2,
+  PBFileOptionsOptimizeModeLiteRuntime = 3,
+} PBFileOptionsOptimizeMode;
+
+BOOL PBFileOptionsOptimizeModeIsValidValue(PBFileOptionsOptimizeMode value);
+
+typedef enum {
+  PBFieldOptionsCTypeString = 0,
+  PBFieldOptionsCTypeCord = 1,
+  PBFieldOptionsCTypeStringPiece = 2,
+} PBFieldOptionsCType;
+
+BOOL PBFieldOptionsCTypeIsValidValue(PBFieldOptionsCType value);
+
+
+@interface PBDescriptorRoot : NSObject {
+}
++ (PBExtensionRegistry*) extensionRegistry;
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry;
+@end
+
+@interface PBFileDescriptorSet : PBGeneratedMessage {
+@private
+  NSMutableArray * fileArray;
+}
+@property (readonly, strong) NSArray * file;
+- (PBFileDescriptorProto*)fileAtIndex:(NSUInteger)index;
+
++ (PBFileDescriptorSet*) defaultInstance;
+- (PBFileDescriptorSet*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBFileDescriptorSetBuilder*) builder;
++ (PBFileDescriptorSetBuilder*) builder;
++ (PBFileDescriptorSetBuilder*) builderWithPrototype:(PBFileDescriptorSet*) prototype;
+- (PBFileDescriptorSetBuilder*) toBuilder;
+
++ (PBFileDescriptorSet*) parseFromData:(NSData*) data;
++ (PBFileDescriptorSet*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFileDescriptorSet*) parseFromInputStream:(NSInputStream*) input;
++ (PBFileDescriptorSet*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFileDescriptorSet*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBFileDescriptorSet*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBFileDescriptorSetBuilder : PBGeneratedMessageBuilder {
+@private
+  PBFileDescriptorSet* result;
+}
+
+- (PBFileDescriptorSet*) defaultInstance;
+
+- (PBFileDescriptorSetBuilder*) clear;
+- (PBFileDescriptorSetBuilder*) clone;
+
+- (PBFileDescriptorSet*) build;
+- (PBFileDescriptorSet*) buildPartial;
+
+- (PBFileDescriptorSetBuilder*) mergeFrom:(PBFileDescriptorSet*) other;
+- (PBFileDescriptorSetBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBFileDescriptorSetBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (NSMutableArray *)file;
+- (PBFileDescriptorProto*)fileAtIndex:(NSUInteger)index;
+- (PBFileDescriptorSetBuilder *)addFile:(PBFileDescriptorProto*)value;
+- (PBFileDescriptorSetBuilder *)setFileArray:(NSArray *)array;
+- (PBFileDescriptorSetBuilder *)clearFile;
+@end
+
+@interface PBFileDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasName_:1;
+  BOOL hasPackage_:1;
+  BOOL hasOptions_:1;
+  BOOL hasSourceCodeInfo_:1;
+  NSString* name;
+  NSString* package;
+  PBFileOptions* options;
+  PBSourceCodeInfo* sourceCodeInfo;
+  PBAppendableArray * publicDependencyArray;
+  PBAppendableArray * weakDependencyArray;
+  NSMutableArray * dependencyArray;
+  NSMutableArray * messageTypeArray;
+  NSMutableArray * enumTypeArray;
+  NSMutableArray * serviceArray;
+  NSMutableArray * extensionArray;
+}
+- (BOOL) hasName;
+- (BOOL) hasPackage;
+- (BOOL) hasOptions;
+- (BOOL) hasSourceCodeInfo;
+@property (readonly, strong) NSString* name;
+@property (readonly, strong) NSString* package;
+@property (readonly, strong) PBArray * dependency;
+@property (readonly, strong) PBArray * publicDependency;
+@property (readonly, strong) PBArray * weakDependency;
+@property (readonly, strong) NSArray * messageType;
+@property (readonly, strong) NSArray * enumType;
+@property (readonly, strong) NSArray * service;
+@property (readonly, strong) NSArray * extension;
+@property (readonly, strong) PBFileOptions* options;
+@property (readonly, strong) PBSourceCodeInfo* sourceCodeInfo;
+- (NSString*)dependencyAtIndex:(NSUInteger)index;
+- (SInt32)publicDependencyAtIndex:(NSUInteger)index;
+- (SInt32)weakDependencyAtIndex:(NSUInteger)index;
+- (PBDescriptorProto*)messageTypeAtIndex:(NSUInteger)index;
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index;
+- (PBServiceDescriptorProto*)serviceAtIndex:(NSUInteger)index;
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index;
+
++ (PBFileDescriptorProto*) defaultInstance;
+- (PBFileDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBFileDescriptorProtoBuilder*) builder;
++ (PBFileDescriptorProtoBuilder*) builder;
++ (PBFileDescriptorProtoBuilder*) builderWithPrototype:(PBFileDescriptorProto*) prototype;
+- (PBFileDescriptorProtoBuilder*) toBuilder;
+
++ (PBFileDescriptorProto*) parseFromData:(NSData*) data;
++ (PBFileDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFileDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBFileDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFileDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBFileDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBFileDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBFileDescriptorProto* result;
+}
+
+- (PBFileDescriptorProto*) defaultInstance;
+
+- (PBFileDescriptorProtoBuilder*) clear;
+- (PBFileDescriptorProtoBuilder*) clone;
+
+- (PBFileDescriptorProto*) build;
+- (PBFileDescriptorProto*) buildPartial;
+
+- (PBFileDescriptorProtoBuilder*) mergeFrom:(PBFileDescriptorProto*) other;
+- (PBFileDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBFileDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBFileDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBFileDescriptorProtoBuilder*) clearName;
+
+- (BOOL) hasPackage;
+- (NSString*) package;
+- (PBFileDescriptorProtoBuilder*) setPackage:(NSString*) value;
+- (PBFileDescriptorProtoBuilder*) clearPackage;
+
+- (NSMutableArray *)dependency;
+- (NSString*)dependencyAtIndex:(NSUInteger)index;
+- (PBFileDescriptorProtoBuilder *)addDependency:(NSString*)value;
+- (PBFileDescriptorProtoBuilder *)setDependencyArray:(NSArray *)array;
+- (PBFileDescriptorProtoBuilder *)clearDependency;
+
+- (PBAppendableArray *)publicDependency;
+- (SInt32)publicDependencyAtIndex:(NSUInteger)index;
+- (PBFileDescriptorProtoBuilder *)addPublicDependency:(SInt32)value;
+- (PBFileDescriptorProtoBuilder *)setPublicDependencyArray:(NSArray *)array;
+- (PBFileDescriptorProtoBuilder *)setPublicDependencyValues:(const SInt32 *)values count:(NSUInteger)count;
+- (PBFileDescriptorProtoBuilder *)clearPublicDependency;
+
+- (PBAppendableArray *)weakDependency;
+- (SInt32)weakDependencyAtIndex:(NSUInteger)index;
+- (PBFileDescriptorProtoBuilder *)addWeakDependency:(SInt32)value;
+- (PBFileDescriptorProtoBuilder *)setWeakDependencyArray:(NSArray *)array;
+- (PBFileDescriptorProtoBuilder *)setWeakDependencyValues:(const SInt32 *)values count:(NSUInteger)count;
+- (PBFileDescriptorProtoBuilder *)clearWeakDependency;
+
+- (NSMutableArray *)messageType;
+- (PBDescriptorProto*)messageTypeAtIndex:(NSUInteger)index;
+- (PBFileDescriptorProtoBuilder *)addMessageType:(PBDescriptorProto*)value;
+- (PBFileDescriptorProtoBuilder *)setMessageTypeArray:(NSArray *)array;
+- (PBFileDescriptorProtoBuilder *)clearMessageType;
+
+- (NSMutableArray *)enumType;
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index;
+- (PBFileDescriptorProtoBuilder *)addEnumType:(PBEnumDescriptorProto*)value;
+- (PBFileDescriptorProtoBuilder *)setEnumTypeArray:(NSArray *)array;
+- (PBFileDescriptorProtoBuilder *)clearEnumType;
+
+- (NSMutableArray *)service;
+- (PBServiceDescriptorProto*)serviceAtIndex:(NSUInteger)index;
+- (PBFileDescriptorProtoBuilder *)addService:(PBServiceDescriptorProto*)value;
+- (PBFileDescriptorProtoBuilder *)setServiceArray:(NSArray *)array;
+- (PBFileDescriptorProtoBuilder *)clearService;
+
+- (NSMutableArray *)extension;
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index;
+- (PBFileDescriptorProtoBuilder *)addExtension:(PBFieldDescriptorProto*)value;
+- (PBFileDescriptorProtoBuilder *)setExtensionArray:(NSArray *)array;
+- (PBFileDescriptorProtoBuilder *)clearExtension;
+
+- (BOOL) hasOptions;
+- (PBFileOptions*) options;
+- (PBFileDescriptorProtoBuilder*) setOptions:(PBFileOptions*) value;
+- (PBFileDescriptorProtoBuilder*) setOptionsBuilder:(PBFileOptionsBuilder*) builderForValue;
+- (PBFileDescriptorProtoBuilder*) mergeOptions:(PBFileOptions*) value;
+- (PBFileDescriptorProtoBuilder*) clearOptions;
+
+- (BOOL) hasSourceCodeInfo;
+- (PBSourceCodeInfo*) sourceCodeInfo;
+- (PBFileDescriptorProtoBuilder*) setSourceCodeInfo:(PBSourceCodeInfo*) value;
+- (PBFileDescriptorProtoBuilder*) setSourceCodeInfoBuilder:(PBSourceCodeInfoBuilder*) builderForValue;
+- (PBFileDescriptorProtoBuilder*) mergeSourceCodeInfo:(PBSourceCodeInfo*) value;
+- (PBFileDescriptorProtoBuilder*) clearSourceCodeInfo;
+@end
+
+@interface PBDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasName_:1;
+  BOOL hasOptions_:1;
+  NSString* name;
+  PBMessageOptions* options;
+  NSMutableArray * fieldArray;
+  NSMutableArray * extensionArray;
+  NSMutableArray * nestedTypeArray;
+  NSMutableArray * enumTypeArray;
+  NSMutableArray * extensionRangeArray;
+  NSMutableArray * oneofDeclArray;
+}
+- (BOOL) hasName;
+- (BOOL) hasOptions;
+@property (readonly, strong) NSString* name;
+@property (readonly, strong) NSArray * field;
+@property (readonly, strong) NSArray * extension;
+@property (readonly, strong) NSArray * nestedType;
+@property (readonly, strong) NSArray * enumType;
+@property (readonly, strong) NSArray * extensionRange;
+@property (readonly, strong) NSArray * oneofDecl;
+@property (readonly, strong) PBMessageOptions* options;
+- (PBFieldDescriptorProto*)fieldAtIndex:(NSUInteger)index;
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index;
+- (PBDescriptorProto*)nestedTypeAtIndex:(NSUInteger)index;
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index;
+- (PBDescriptorProtoExtensionRange*)extensionRangeAtIndex:(NSUInteger)index;
+- (PBOneofDescriptorProto*)oneofDeclAtIndex:(NSUInteger)index;
+
++ (PBDescriptorProto*) defaultInstance;
+- (PBDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBDescriptorProtoBuilder*) builder;
++ (PBDescriptorProtoBuilder*) builder;
++ (PBDescriptorProtoBuilder*) builderWithPrototype:(PBDescriptorProto*) prototype;
+- (PBDescriptorProtoBuilder*) toBuilder;
+
++ (PBDescriptorProto*) parseFromData:(NSData*) data;
++ (PBDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBDescriptorProtoExtensionRange : PBGeneratedMessage {
+@private
+  BOOL hasStart_:1;
+  BOOL hasEnd_:1;
+  SInt32 start;
+  SInt32 end;
+}
+- (BOOL) hasStart;
+- (BOOL) hasEnd;
+@property (readonly) SInt32 start;
+@property (readonly) SInt32 end;
+
++ (PBDescriptorProtoExtensionRange*) defaultInstance;
+- (PBDescriptorProtoExtensionRange*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBDescriptorProtoExtensionRangeBuilder*) builder;
++ (PBDescriptorProtoExtensionRangeBuilder*) builder;
++ (PBDescriptorProtoExtensionRangeBuilder*) builderWithPrototype:(PBDescriptorProtoExtensionRange*) prototype;
+- (PBDescriptorProtoExtensionRangeBuilder*) toBuilder;
+
++ (PBDescriptorProtoExtensionRange*) parseFromData:(NSData*) data;
++ (PBDescriptorProtoExtensionRange*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBDescriptorProtoExtensionRange*) parseFromInputStream:(NSInputStream*) input;
++ (PBDescriptorProtoExtensionRange*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBDescriptorProtoExtensionRange*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBDescriptorProtoExtensionRange*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBDescriptorProtoExtensionRangeBuilder : PBGeneratedMessageBuilder {
+@private
+  PBDescriptorProtoExtensionRange* result;
+}
+
+- (PBDescriptorProtoExtensionRange*) defaultInstance;
+
+- (PBDescriptorProtoExtensionRangeBuilder*) clear;
+- (PBDescriptorProtoExtensionRangeBuilder*) clone;
+
+- (PBDescriptorProtoExtensionRange*) build;
+- (PBDescriptorProtoExtensionRange*) buildPartial;
+
+- (PBDescriptorProtoExtensionRangeBuilder*) mergeFrom:(PBDescriptorProtoExtensionRange*) other;
+- (PBDescriptorProtoExtensionRangeBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBDescriptorProtoExtensionRangeBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasStart;
+- (SInt32) start;
+- (PBDescriptorProtoExtensionRangeBuilder*) setStart:(SInt32) value;
+- (PBDescriptorProtoExtensionRangeBuilder*) clearStart;
+
+- (BOOL) hasEnd;
+- (SInt32) end;
+- (PBDescriptorProtoExtensionRangeBuilder*) setEnd:(SInt32) value;
+- (PBDescriptorProtoExtensionRangeBuilder*) clearEnd;
+@end
+
+@interface PBDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBDescriptorProto* result;
+}
+
+- (PBDescriptorProto*) defaultInstance;
+
+- (PBDescriptorProtoBuilder*) clear;
+- (PBDescriptorProtoBuilder*) clone;
+
+- (PBDescriptorProto*) build;
+- (PBDescriptorProto*) buildPartial;
+
+- (PBDescriptorProtoBuilder*) mergeFrom:(PBDescriptorProto*) other;
+- (PBDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBDescriptorProtoBuilder*) clearName;
+
+- (NSMutableArray *)field;
+- (PBFieldDescriptorProto*)fieldAtIndex:(NSUInteger)index;
+- (PBDescriptorProtoBuilder *)addField:(PBFieldDescriptorProto*)value;
+- (PBDescriptorProtoBuilder *)setFieldArray:(NSArray *)array;
+- (PBDescriptorProtoBuilder *)clearField;
+
+- (NSMutableArray *)extension;
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index;
+- (PBDescriptorProtoBuilder *)addExtension:(PBFieldDescriptorProto*)value;
+- (PBDescriptorProtoBuilder *)setExtensionArray:(NSArray *)array;
+- (PBDescriptorProtoBuilder *)clearExtension;
+
+- (NSMutableArray *)nestedType;
+- (PBDescriptorProto*)nestedTypeAtIndex:(NSUInteger)index;
+- (PBDescriptorProtoBuilder *)addNestedType:(PBDescriptorProto*)value;
+- (PBDescriptorProtoBuilder *)setNestedTypeArray:(NSArray *)array;
+- (PBDescriptorProtoBuilder *)clearNestedType;
+
+- (NSMutableArray *)enumType;
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index;
+- (PBDescriptorProtoBuilder *)addEnumType:(PBEnumDescriptorProto*)value;
+- (PBDescriptorProtoBuilder *)setEnumTypeArray:(NSArray *)array;
+- (PBDescriptorProtoBuilder *)clearEnumType;
+
+- (NSMutableArray *)extensionRange;
+- (PBDescriptorProtoExtensionRange*)extensionRangeAtIndex:(NSUInteger)index;
+- (PBDescriptorProtoBuilder *)addExtensionRange:(PBDescriptorProtoExtensionRange*)value;
+- (PBDescriptorProtoBuilder *)setExtensionRangeArray:(NSArray *)array;
+- (PBDescriptorProtoBuilder *)clearExtensionRange;
+
+- (NSMutableArray *)oneofDecl;
+- (PBOneofDescriptorProto*)oneofDeclAtIndex:(NSUInteger)index;
+- (PBDescriptorProtoBuilder *)addOneofDecl:(PBOneofDescriptorProto*)value;
+- (PBDescriptorProtoBuilder *)setOneofDeclArray:(NSArray *)array;
+- (PBDescriptorProtoBuilder *)clearOneofDecl;
+
+- (BOOL) hasOptions;
+- (PBMessageOptions*) options;
+- (PBDescriptorProtoBuilder*) setOptions:(PBMessageOptions*) value;
+- (PBDescriptorProtoBuilder*) setOptionsBuilder:(PBMessageOptionsBuilder*) builderForValue;
+- (PBDescriptorProtoBuilder*) mergeOptions:(PBMessageOptions*) value;
+- (PBDescriptorProtoBuilder*) clearOptions;
+@end
+
+@interface PBFieldDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasNumber_:1;
+  BOOL hasOneofIndex_:1;
+  BOOL hasName_:1;
+  BOOL hasTypeName_:1;
+  BOOL hasExtendee_:1;
+  BOOL hasDefaultValue_:1;
+  BOOL hasOptions_:1;
+  BOOL hasLabel_:1;
+  BOOL hasType_:1;
+  SInt32 number;
+  SInt32 oneofIndex;
+  NSString* name;
+  NSString* typeName;
+  NSString* extendee;
+  NSString* defaultValue;
+  PBFieldOptions* options;
+  PBFieldDescriptorProtoLabel label;
+  PBFieldDescriptorProtoType type;
+}
+- (BOOL) hasName;
+- (BOOL) hasNumber;
+- (BOOL) hasLabel;
+- (BOOL) hasType;
+- (BOOL) hasTypeName;
+- (BOOL) hasExtendee;
+- (BOOL) hasDefaultValue;
+- (BOOL) hasOneofIndex;
+- (BOOL) hasOptions;
+@property (readonly, strong) NSString* name;
+@property (readonly) SInt32 number;
+@property (readonly) PBFieldDescriptorProtoLabel label;
+@property (readonly) PBFieldDescriptorProtoType type;
+@property (readonly, strong) NSString* typeName;
+@property (readonly, strong) NSString* extendee;
+@property (readonly, strong) NSString* defaultValue;
+@property (readonly) SInt32 oneofIndex;
+@property (readonly, strong) PBFieldOptions* options;
+
++ (PBFieldDescriptorProto*) defaultInstance;
+- (PBFieldDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBFieldDescriptorProtoBuilder*) builder;
++ (PBFieldDescriptorProtoBuilder*) builder;
++ (PBFieldDescriptorProtoBuilder*) builderWithPrototype:(PBFieldDescriptorProto*) prototype;
+- (PBFieldDescriptorProtoBuilder*) toBuilder;
+
++ (PBFieldDescriptorProto*) parseFromData:(NSData*) data;
++ (PBFieldDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFieldDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBFieldDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFieldDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBFieldDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBFieldDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBFieldDescriptorProto* result;
+}
+
+- (PBFieldDescriptorProto*) defaultInstance;
+
+- (PBFieldDescriptorProtoBuilder*) clear;
+- (PBFieldDescriptorProtoBuilder*) clone;
+
+- (PBFieldDescriptorProto*) build;
+- (PBFieldDescriptorProto*) buildPartial;
+
+- (PBFieldDescriptorProtoBuilder*) mergeFrom:(PBFieldDescriptorProto*) other;
+- (PBFieldDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBFieldDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBFieldDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBFieldDescriptorProtoBuilder*) clearName;
+
+- (BOOL) hasNumber;
+- (SInt32) number;
+- (PBFieldDescriptorProtoBuilder*) setNumber:(SInt32) value;
+- (PBFieldDescriptorProtoBuilder*) clearNumber;
+
+- (BOOL) hasLabel;
+- (PBFieldDescriptorProtoLabel) label;
+- (PBFieldDescriptorProtoBuilder*) setLabel:(PBFieldDescriptorProtoLabel) value;
+- (PBFieldDescriptorProtoBuilder*) clearLabel;
+
+- (BOOL) hasType;
+- (PBFieldDescriptorProtoType) type;
+- (PBFieldDescriptorProtoBuilder*) setType:(PBFieldDescriptorProtoType) value;
+- (PBFieldDescriptorProtoBuilder*) clearType;
+
+- (BOOL) hasTypeName;
+- (NSString*) typeName;
+- (PBFieldDescriptorProtoBuilder*) setTypeName:(NSString*) value;
+- (PBFieldDescriptorProtoBuilder*) clearTypeName;
+
+- (BOOL) hasExtendee;
+- (NSString*) extendee;
+- (PBFieldDescriptorProtoBuilder*) setExtendee:(NSString*) value;
+- (PBFieldDescriptorProtoBuilder*) clearExtendee;
+
+- (BOOL) hasDefaultValue;
+- (NSString*) defaultValue;
+- (PBFieldDescriptorProtoBuilder*) setDefaultValue:(NSString*) value;
+- (PBFieldDescriptorProtoBuilder*) clearDefaultValue;
+
+- (BOOL) hasOneofIndex;
+- (SInt32) oneofIndex;
+- (PBFieldDescriptorProtoBuilder*) setOneofIndex:(SInt32) value;
+- (PBFieldDescriptorProtoBuilder*) clearOneofIndex;
+
+- (BOOL) hasOptions;
+- (PBFieldOptions*) options;
+- (PBFieldDescriptorProtoBuilder*) setOptions:(PBFieldOptions*) value;
+- (PBFieldDescriptorProtoBuilder*) setOptionsBuilder:(PBFieldOptionsBuilder*) builderForValue;
+- (PBFieldDescriptorProtoBuilder*) mergeOptions:(PBFieldOptions*) value;
+- (PBFieldDescriptorProtoBuilder*) clearOptions;
+@end
+
+@interface PBOneofDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasName_:1;
+  NSString* name;
+}
+- (BOOL) hasName;
+@property (readonly, strong) NSString* name;
+
++ (PBOneofDescriptorProto*) defaultInstance;
+- (PBOneofDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBOneofDescriptorProtoBuilder*) builder;
++ (PBOneofDescriptorProtoBuilder*) builder;
++ (PBOneofDescriptorProtoBuilder*) builderWithPrototype:(PBOneofDescriptorProto*) prototype;
+- (PBOneofDescriptorProtoBuilder*) toBuilder;
+
++ (PBOneofDescriptorProto*) parseFromData:(NSData*) data;
++ (PBOneofDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBOneofDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBOneofDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBOneofDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBOneofDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBOneofDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBOneofDescriptorProto* result;
+}
+
+- (PBOneofDescriptorProto*) defaultInstance;
+
+- (PBOneofDescriptorProtoBuilder*) clear;
+- (PBOneofDescriptorProtoBuilder*) clone;
+
+- (PBOneofDescriptorProto*) build;
+- (PBOneofDescriptorProto*) buildPartial;
+
+- (PBOneofDescriptorProtoBuilder*) mergeFrom:(PBOneofDescriptorProto*) other;
+- (PBOneofDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBOneofDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBOneofDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBOneofDescriptorProtoBuilder*) clearName;
+@end
+
+@interface PBEnumDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasName_:1;
+  BOOL hasOptions_:1;
+  NSString* name;
+  PBEnumOptions* options;
+  NSMutableArray * valueArray;
+}
+- (BOOL) hasName;
+- (BOOL) hasOptions;
+@property (readonly, strong) NSString* name;
+@property (readonly, strong) NSArray * value;
+@property (readonly, strong) PBEnumOptions* options;
+- (PBEnumValueDescriptorProto*)valueAtIndex:(NSUInteger)index;
+
++ (PBEnumDescriptorProto*) defaultInstance;
+- (PBEnumDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBEnumDescriptorProtoBuilder*) builder;
++ (PBEnumDescriptorProtoBuilder*) builder;
++ (PBEnumDescriptorProtoBuilder*) builderWithPrototype:(PBEnumDescriptorProto*) prototype;
+- (PBEnumDescriptorProtoBuilder*) toBuilder;
+
++ (PBEnumDescriptorProto*) parseFromData:(NSData*) data;
++ (PBEnumDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBEnumDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBEnumDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBEnumDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBEnumDescriptorProto* result;
+}
+
+- (PBEnumDescriptorProto*) defaultInstance;
+
+- (PBEnumDescriptorProtoBuilder*) clear;
+- (PBEnumDescriptorProtoBuilder*) clone;
+
+- (PBEnumDescriptorProto*) build;
+- (PBEnumDescriptorProto*) buildPartial;
+
+- (PBEnumDescriptorProtoBuilder*) mergeFrom:(PBEnumDescriptorProto*) other;
+- (PBEnumDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBEnumDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBEnumDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBEnumDescriptorProtoBuilder*) clearName;
+
+- (NSMutableArray *)value;
+- (PBEnumValueDescriptorProto*)valueAtIndex:(NSUInteger)index;
+- (PBEnumDescriptorProtoBuilder *)addValue:(PBEnumValueDescriptorProto*)value;
+- (PBEnumDescriptorProtoBuilder *)setValueArray:(NSArray *)array;
+- (PBEnumDescriptorProtoBuilder *)clearValue;
+
+- (BOOL) hasOptions;
+- (PBEnumOptions*) options;
+- (PBEnumDescriptorProtoBuilder*) setOptions:(PBEnumOptions*) value;
+- (PBEnumDescriptorProtoBuilder*) setOptionsBuilder:(PBEnumOptionsBuilder*) builderForValue;
+- (PBEnumDescriptorProtoBuilder*) mergeOptions:(PBEnumOptions*) value;
+- (PBEnumDescriptorProtoBuilder*) clearOptions;
+@end
+
+@interface PBEnumValueDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasNumber_:1;
+  BOOL hasName_:1;
+  BOOL hasOptions_:1;
+  SInt32 number;
+  NSString* name;
+  PBEnumValueOptions* options;
+}
+- (BOOL) hasName;
+- (BOOL) hasNumber;
+- (BOOL) hasOptions;
+@property (readonly, strong) NSString* name;
+@property (readonly) SInt32 number;
+@property (readonly, strong) PBEnumValueOptions* options;
+
++ (PBEnumValueDescriptorProto*) defaultInstance;
+- (PBEnumValueDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBEnumValueDescriptorProtoBuilder*) builder;
++ (PBEnumValueDescriptorProtoBuilder*) builder;
++ (PBEnumValueDescriptorProtoBuilder*) builderWithPrototype:(PBEnumValueDescriptorProto*) prototype;
+- (PBEnumValueDescriptorProtoBuilder*) toBuilder;
+
++ (PBEnumValueDescriptorProto*) parseFromData:(NSData*) data;
++ (PBEnumValueDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumValueDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBEnumValueDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumValueDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBEnumValueDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBEnumValueDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBEnumValueDescriptorProto* result;
+}
+
+- (PBEnumValueDescriptorProto*) defaultInstance;
+
+- (PBEnumValueDescriptorProtoBuilder*) clear;
+- (PBEnumValueDescriptorProtoBuilder*) clone;
+
+- (PBEnumValueDescriptorProto*) build;
+- (PBEnumValueDescriptorProto*) buildPartial;
+
+- (PBEnumValueDescriptorProtoBuilder*) mergeFrom:(PBEnumValueDescriptorProto*) other;
+- (PBEnumValueDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBEnumValueDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBEnumValueDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBEnumValueDescriptorProtoBuilder*) clearName;
+
+- (BOOL) hasNumber;
+- (SInt32) number;
+- (PBEnumValueDescriptorProtoBuilder*) setNumber:(SInt32) value;
+- (PBEnumValueDescriptorProtoBuilder*) clearNumber;
+
+- (BOOL) hasOptions;
+- (PBEnumValueOptions*) options;
+- (PBEnumValueDescriptorProtoBuilder*) setOptions:(PBEnumValueOptions*) value;
+- (PBEnumValueDescriptorProtoBuilder*) setOptionsBuilder:(PBEnumValueOptionsBuilder*) builderForValue;
+- (PBEnumValueDescriptorProtoBuilder*) mergeOptions:(PBEnumValueOptions*) value;
+- (PBEnumValueDescriptorProtoBuilder*) clearOptions;
+@end
+
+@interface PBServiceDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasName_:1;
+  BOOL hasOptions_:1;
+  NSString* name;
+  PBServiceOptions* options;
+  NSMutableArray * methodArray;
+}
+- (BOOL) hasName;
+- (BOOL) hasOptions;
+@property (readonly, strong) NSString* name;
+@property (readonly, strong) NSArray * method;
+@property (readonly, strong) PBServiceOptions* options;
+- (PBMethodDescriptorProto*)methodAtIndex:(NSUInteger)index;
+
++ (PBServiceDescriptorProto*) defaultInstance;
+- (PBServiceDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBServiceDescriptorProtoBuilder*) builder;
++ (PBServiceDescriptorProtoBuilder*) builder;
++ (PBServiceDescriptorProtoBuilder*) builderWithPrototype:(PBServiceDescriptorProto*) prototype;
+- (PBServiceDescriptorProtoBuilder*) toBuilder;
+
++ (PBServiceDescriptorProto*) parseFromData:(NSData*) data;
++ (PBServiceDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBServiceDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBServiceDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBServiceDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBServiceDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBServiceDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBServiceDescriptorProto* result;
+}
+
+- (PBServiceDescriptorProto*) defaultInstance;
+
+- (PBServiceDescriptorProtoBuilder*) clear;
+- (PBServiceDescriptorProtoBuilder*) clone;
+
+- (PBServiceDescriptorProto*) build;
+- (PBServiceDescriptorProto*) buildPartial;
+
+- (PBServiceDescriptorProtoBuilder*) mergeFrom:(PBServiceDescriptorProto*) other;
+- (PBServiceDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBServiceDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBServiceDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBServiceDescriptorProtoBuilder*) clearName;
+
+- (NSMutableArray *)method;
+- (PBMethodDescriptorProto*)methodAtIndex:(NSUInteger)index;
+- (PBServiceDescriptorProtoBuilder *)addMethod:(PBMethodDescriptorProto*)value;
+- (PBServiceDescriptorProtoBuilder *)setMethodArray:(NSArray *)array;
+- (PBServiceDescriptorProtoBuilder *)clearMethod;
+
+- (BOOL) hasOptions;
+- (PBServiceOptions*) options;
+- (PBServiceDescriptorProtoBuilder*) setOptions:(PBServiceOptions*) value;
+- (PBServiceDescriptorProtoBuilder*) setOptionsBuilder:(PBServiceOptionsBuilder*) builderForValue;
+- (PBServiceDescriptorProtoBuilder*) mergeOptions:(PBServiceOptions*) value;
+- (PBServiceDescriptorProtoBuilder*) clearOptions;
+@end
+
+@interface PBMethodDescriptorProto : PBGeneratedMessage {
+@private
+  BOOL hasName_:1;
+  BOOL hasInputType_:1;
+  BOOL hasOutputType_:1;
+  BOOL hasOptions_:1;
+  NSString* name;
+  NSString* inputType;
+  NSString* outputType;
+  PBMethodOptions* options;
+}
+- (BOOL) hasName;
+- (BOOL) hasInputType;
+- (BOOL) hasOutputType;
+- (BOOL) hasOptions;
+@property (readonly, strong) NSString* name;
+@property (readonly, strong) NSString* inputType;
+@property (readonly, strong) NSString* outputType;
+@property (readonly, strong) PBMethodOptions* options;
+
++ (PBMethodDescriptorProto*) defaultInstance;
+- (PBMethodDescriptorProto*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBMethodDescriptorProtoBuilder*) builder;
++ (PBMethodDescriptorProtoBuilder*) builder;
++ (PBMethodDescriptorProtoBuilder*) builderWithPrototype:(PBMethodDescriptorProto*) prototype;
+- (PBMethodDescriptorProtoBuilder*) toBuilder;
+
++ (PBMethodDescriptorProto*) parseFromData:(NSData*) data;
++ (PBMethodDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBMethodDescriptorProto*) parseFromInputStream:(NSInputStream*) input;
++ (PBMethodDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBMethodDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBMethodDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBMethodDescriptorProtoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBMethodDescriptorProto* result;
+}
+
+- (PBMethodDescriptorProto*) defaultInstance;
+
+- (PBMethodDescriptorProtoBuilder*) clear;
+- (PBMethodDescriptorProtoBuilder*) clone;
+
+- (PBMethodDescriptorProto*) build;
+- (PBMethodDescriptorProto*) buildPartial;
+
+- (PBMethodDescriptorProtoBuilder*) mergeFrom:(PBMethodDescriptorProto*) other;
+- (PBMethodDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBMethodDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasName;
+- (NSString*) name;
+- (PBMethodDescriptorProtoBuilder*) setName:(NSString*) value;
+- (PBMethodDescriptorProtoBuilder*) clearName;
+
+- (BOOL) hasInputType;
+- (NSString*) inputType;
+- (PBMethodDescriptorProtoBuilder*) setInputType:(NSString*) value;
+- (PBMethodDescriptorProtoBuilder*) clearInputType;
+
+- (BOOL) hasOutputType;
+- (NSString*) outputType;
+- (PBMethodDescriptorProtoBuilder*) setOutputType:(NSString*) value;
+- (PBMethodDescriptorProtoBuilder*) clearOutputType;
+
+- (BOOL) hasOptions;
+- (PBMethodOptions*) options;
+- (PBMethodDescriptorProtoBuilder*) setOptions:(PBMethodOptions*) value;
+- (PBMethodDescriptorProtoBuilder*) setOptionsBuilder:(PBMethodOptionsBuilder*) builderForValue;
+- (PBMethodDescriptorProtoBuilder*) mergeOptions:(PBMethodOptions*) value;
+- (PBMethodDescriptorProtoBuilder*) clearOptions;
+@end
+
+@interface PBFileOptions : PBExtendableMessage {
+@private
+  BOOL hasJavaMultipleFiles_:1;
+  BOOL hasJavaGenerateEqualsAndHash_:1;
+  BOOL hasJavaStringCheckUtf8_:1;
+  BOOL hasCcGenericServices_:1;
+  BOOL hasJavaGenericServices_:1;
+  BOOL hasPyGenericServices_:1;
+  BOOL hasDeprecated_:1;
+  BOOL hasJavaPackage_:1;
+  BOOL hasJavaOuterClassname_:1;
+  BOOL hasGoPackage_:1;
+  BOOL hasOptimizeFor_:1;
+  BOOL javaMultipleFiles_:1;
+  BOOL javaGenerateEqualsAndHash_:1;
+  BOOL javaStringCheckUtf8_:1;
+  BOOL ccGenericServices_:1;
+  BOOL javaGenericServices_:1;
+  BOOL pyGenericServices_:1;
+  BOOL deprecated_:1;
+  NSString* javaPackage;
+  NSString* javaOuterClassname;
+  NSString* goPackage;
+  PBFileOptionsOptimizeMode optimizeFor;
+  NSMutableArray * uninterpretedOptionArray;
+}
+- (BOOL) hasJavaPackage;
+- (BOOL) hasJavaOuterClassname;
+- (BOOL) hasJavaMultipleFiles;
+- (BOOL) hasJavaGenerateEqualsAndHash;
+- (BOOL) hasJavaStringCheckUtf8;
+- (BOOL) hasOptimizeFor;
+- (BOOL) hasGoPackage;
+- (BOOL) hasCcGenericServices;
+- (BOOL) hasJavaGenericServices;
+- (BOOL) hasPyGenericServices;
+- (BOOL) hasDeprecated;
+@property (readonly, strong) NSString* javaPackage;
+@property (readonly, strong) NSString* javaOuterClassname;
+- (BOOL) javaMultipleFiles;
+- (BOOL) javaGenerateEqualsAndHash;
+- (BOOL) javaStringCheckUtf8;
+@property (readonly) PBFileOptionsOptimizeMode optimizeFor;
+@property (readonly, strong) NSString* goPackage;
+- (BOOL) ccGenericServices;
+- (BOOL) javaGenericServices;
+- (BOOL) pyGenericServices;
+- (BOOL) deprecated;
+@property (readonly, strong) NSArray * uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+
++ (PBFileOptions*) defaultInstance;
+- (PBFileOptions*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBFileOptionsBuilder*) builder;
++ (PBFileOptionsBuilder*) builder;
++ (PBFileOptionsBuilder*) builderWithPrototype:(PBFileOptions*) prototype;
+- (PBFileOptionsBuilder*) toBuilder;
+
++ (PBFileOptions*) parseFromData:(NSData*) data;
++ (PBFileOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFileOptions*) parseFromInputStream:(NSInputStream*) input;
++ (PBFileOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFileOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBFileOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBFileOptionsBuilder : PBExtendableMessageBuilder {
+@private
+  PBFileOptions* result;
+}
+
+- (PBFileOptions*) defaultInstance;
+
+- (PBFileOptionsBuilder*) clear;
+- (PBFileOptionsBuilder*) clone;
+
+- (PBFileOptions*) build;
+- (PBFileOptions*) buildPartial;
+
+- (PBFileOptionsBuilder*) mergeFrom:(PBFileOptions*) other;
+- (PBFileOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBFileOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasJavaPackage;
+- (NSString*) javaPackage;
+- (PBFileOptionsBuilder*) setJavaPackage:(NSString*) value;
+- (PBFileOptionsBuilder*) clearJavaPackage;
+
+- (BOOL) hasJavaOuterClassname;
+- (NSString*) javaOuterClassname;
+- (PBFileOptionsBuilder*) setJavaOuterClassname:(NSString*) value;
+- (PBFileOptionsBuilder*) clearJavaOuterClassname;
+
+- (BOOL) hasJavaMultipleFiles;
+- (BOOL) javaMultipleFiles;
+- (PBFileOptionsBuilder*) setJavaMultipleFiles:(BOOL) value;
+- (PBFileOptionsBuilder*) clearJavaMultipleFiles;
+
+- (BOOL) hasJavaGenerateEqualsAndHash;
+- (BOOL) javaGenerateEqualsAndHash;
+- (PBFileOptionsBuilder*) setJavaGenerateEqualsAndHash:(BOOL) value;
+- (PBFileOptionsBuilder*) clearJavaGenerateEqualsAndHash;
+
+- (BOOL) hasJavaStringCheckUtf8;
+- (BOOL) javaStringCheckUtf8;
+- (PBFileOptionsBuilder*) setJavaStringCheckUtf8:(BOOL) value;
+- (PBFileOptionsBuilder*) clearJavaStringCheckUtf8;
+
+- (BOOL) hasOptimizeFor;
+- (PBFileOptionsOptimizeMode) optimizeFor;
+- (PBFileOptionsBuilder*) setOptimizeFor:(PBFileOptionsOptimizeMode) value;
+- (PBFileOptionsBuilder*) clearOptimizeFor;
+
+- (BOOL) hasGoPackage;
+- (NSString*) goPackage;
+- (PBFileOptionsBuilder*) setGoPackage:(NSString*) value;
+- (PBFileOptionsBuilder*) clearGoPackage;
+
+- (BOOL) hasCcGenericServices;
+- (BOOL) ccGenericServices;
+- (PBFileOptionsBuilder*) setCcGenericServices:(BOOL) value;
+- (PBFileOptionsBuilder*) clearCcGenericServices;
+
+- (BOOL) hasJavaGenericServices;
+- (BOOL) javaGenericServices;
+- (PBFileOptionsBuilder*) setJavaGenericServices:(BOOL) value;
+- (PBFileOptionsBuilder*) clearJavaGenericServices;
+
+- (BOOL) hasPyGenericServices;
+- (BOOL) pyGenericServices;
+- (PBFileOptionsBuilder*) setPyGenericServices:(BOOL) value;
+- (PBFileOptionsBuilder*) clearPyGenericServices;
+
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+- (PBFileOptionsBuilder*) setDeprecated:(BOOL) value;
+- (PBFileOptionsBuilder*) clearDeprecated;
+
+- (NSMutableArray *)uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+- (PBFileOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value;
+- (PBFileOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array;
+- (PBFileOptionsBuilder *)clearUninterpretedOption;
+@end
+
+@interface PBMessageOptions : PBExtendableMessage {
+@private
+  BOOL hasMessageSetWireFormat_:1;
+  BOOL hasNoStandardDescriptorAccessor_:1;
+  BOOL hasDeprecated_:1;
+  BOOL messageSetWireFormat_:1;
+  BOOL noStandardDescriptorAccessor_:1;
+  BOOL deprecated_:1;
+  NSMutableArray * uninterpretedOptionArray;
+}
+- (BOOL) hasMessageSetWireFormat;
+- (BOOL) hasNoStandardDescriptorAccessor;
+- (BOOL) hasDeprecated;
+- (BOOL) messageSetWireFormat;
+- (BOOL) noStandardDescriptorAccessor;
+- (BOOL) deprecated;
+@property (readonly, strong) NSArray * uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+
++ (PBMessageOptions*) defaultInstance;
+- (PBMessageOptions*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBMessageOptionsBuilder*) builder;
++ (PBMessageOptionsBuilder*) builder;
++ (PBMessageOptionsBuilder*) builderWithPrototype:(PBMessageOptions*) prototype;
+- (PBMessageOptionsBuilder*) toBuilder;
+
++ (PBMessageOptions*) parseFromData:(NSData*) data;
++ (PBMessageOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBMessageOptions*) parseFromInputStream:(NSInputStream*) input;
++ (PBMessageOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBMessageOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBMessageOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBMessageOptionsBuilder : PBExtendableMessageBuilder {
+@private
+  PBMessageOptions* result;
+}
+
+- (PBMessageOptions*) defaultInstance;
+
+- (PBMessageOptionsBuilder*) clear;
+- (PBMessageOptionsBuilder*) clone;
+
+- (PBMessageOptions*) build;
+- (PBMessageOptions*) buildPartial;
+
+- (PBMessageOptionsBuilder*) mergeFrom:(PBMessageOptions*) other;
+- (PBMessageOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBMessageOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasMessageSetWireFormat;
+- (BOOL) messageSetWireFormat;
+- (PBMessageOptionsBuilder*) setMessageSetWireFormat:(BOOL) value;
+- (PBMessageOptionsBuilder*) clearMessageSetWireFormat;
+
+- (BOOL) hasNoStandardDescriptorAccessor;
+- (BOOL) noStandardDescriptorAccessor;
+- (PBMessageOptionsBuilder*) setNoStandardDescriptorAccessor:(BOOL) value;
+- (PBMessageOptionsBuilder*) clearNoStandardDescriptorAccessor;
+
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+- (PBMessageOptionsBuilder*) setDeprecated:(BOOL) value;
+- (PBMessageOptionsBuilder*) clearDeprecated;
+
+- (NSMutableArray *)uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+- (PBMessageOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value;
+- (PBMessageOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array;
+- (PBMessageOptionsBuilder *)clearUninterpretedOption;
+@end
+
+@interface PBFieldOptions : PBExtendableMessage {
+@private
+  BOOL hasPacked_:1;
+  BOOL hasLazy_:1;
+  BOOL hasDeprecated_:1;
+  BOOL hasWeak_:1;
+  BOOL hasExperimentalMapKey_:1;
+  BOOL hasCtype_:1;
+  BOOL packed_:1;
+  BOOL lazy_:1;
+  BOOL deprecated_:1;
+  BOOL weak_:1;
+  NSString* experimentalMapKey;
+  PBFieldOptionsCType ctype;
+  NSMutableArray * uninterpretedOptionArray;
+}
+- (BOOL) hasCtype;
+- (BOOL) hasPacked;
+- (BOOL) hasLazy;
+- (BOOL) hasDeprecated;
+- (BOOL) hasExperimentalMapKey;
+- (BOOL) hasWeak;
+@property (readonly) PBFieldOptionsCType ctype;
+- (BOOL) packed;
+- (BOOL) lazy;
+- (BOOL) deprecated;
+@property (readonly, strong) NSString* experimentalMapKey;
+- (BOOL) weak;
+@property (readonly, strong) NSArray * uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+
++ (PBFieldOptions*) defaultInstance;
+- (PBFieldOptions*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBFieldOptionsBuilder*) builder;
++ (PBFieldOptionsBuilder*) builder;
++ (PBFieldOptionsBuilder*) builderWithPrototype:(PBFieldOptions*) prototype;
+- (PBFieldOptionsBuilder*) toBuilder;
+
++ (PBFieldOptions*) parseFromData:(NSData*) data;
++ (PBFieldOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFieldOptions*) parseFromInputStream:(NSInputStream*) input;
++ (PBFieldOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBFieldOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBFieldOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBFieldOptionsBuilder : PBExtendableMessageBuilder {
+@private
+  PBFieldOptions* result;
+}
+
+- (PBFieldOptions*) defaultInstance;
+
+- (PBFieldOptionsBuilder*) clear;
+- (PBFieldOptionsBuilder*) clone;
+
+- (PBFieldOptions*) build;
+- (PBFieldOptions*) buildPartial;
+
+- (PBFieldOptionsBuilder*) mergeFrom:(PBFieldOptions*) other;
+- (PBFieldOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBFieldOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasCtype;
+- (PBFieldOptionsCType) ctype;
+- (PBFieldOptionsBuilder*) setCtype:(PBFieldOptionsCType) value;
+- (PBFieldOptionsBuilder*) clearCtype;
+
+- (BOOL) hasPacked;
+- (BOOL) packed;
+- (PBFieldOptionsBuilder*) setPacked:(BOOL) value;
+- (PBFieldOptionsBuilder*) clearPacked;
+
+- (BOOL) hasLazy;
+- (BOOL) lazy;
+- (PBFieldOptionsBuilder*) setLazy:(BOOL) value;
+- (PBFieldOptionsBuilder*) clearLazy;
+
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+- (PBFieldOptionsBuilder*) setDeprecated:(BOOL) value;
+- (PBFieldOptionsBuilder*) clearDeprecated;
+
+- (BOOL) hasExperimentalMapKey;
+- (NSString*) experimentalMapKey;
+- (PBFieldOptionsBuilder*) setExperimentalMapKey:(NSString*) value;
+- (PBFieldOptionsBuilder*) clearExperimentalMapKey;
+
+- (BOOL) hasWeak;
+- (BOOL) weak;
+- (PBFieldOptionsBuilder*) setWeak:(BOOL) value;
+- (PBFieldOptionsBuilder*) clearWeak;
+
+- (NSMutableArray *)uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+- (PBFieldOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value;
+- (PBFieldOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array;
+- (PBFieldOptionsBuilder *)clearUninterpretedOption;
+@end
+
+@interface PBEnumOptions : PBExtendableMessage {
+@private
+  BOOL hasAllowAlias_:1;
+  BOOL hasDeprecated_:1;
+  BOOL allowAlias_:1;
+  BOOL deprecated_:1;
+  NSMutableArray * uninterpretedOptionArray;
+}
+- (BOOL) hasAllowAlias;
+- (BOOL) hasDeprecated;
+- (BOOL) allowAlias;
+- (BOOL) deprecated;
+@property (readonly, strong) NSArray * uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+
++ (PBEnumOptions*) defaultInstance;
+- (PBEnumOptions*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBEnumOptionsBuilder*) builder;
++ (PBEnumOptionsBuilder*) builder;
++ (PBEnumOptionsBuilder*) builderWithPrototype:(PBEnumOptions*) prototype;
+- (PBEnumOptionsBuilder*) toBuilder;
+
++ (PBEnumOptions*) parseFromData:(NSData*) data;
++ (PBEnumOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumOptions*) parseFromInputStream:(NSInputStream*) input;
++ (PBEnumOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBEnumOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBEnumOptionsBuilder : PBExtendableMessageBuilder {
+@private
+  PBEnumOptions* result;
+}
+
+- (PBEnumOptions*) defaultInstance;
+
+- (PBEnumOptionsBuilder*) clear;
+- (PBEnumOptionsBuilder*) clone;
+
+- (PBEnumOptions*) build;
+- (PBEnumOptions*) buildPartial;
+
+- (PBEnumOptionsBuilder*) mergeFrom:(PBEnumOptions*) other;
+- (PBEnumOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBEnumOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasAllowAlias;
+- (BOOL) allowAlias;
+- (PBEnumOptionsBuilder*) setAllowAlias:(BOOL) value;
+- (PBEnumOptionsBuilder*) clearAllowAlias;
+
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+- (PBEnumOptionsBuilder*) setDeprecated:(BOOL) value;
+- (PBEnumOptionsBuilder*) clearDeprecated;
+
+- (NSMutableArray *)uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+- (PBEnumOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value;
+- (PBEnumOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array;
+- (PBEnumOptionsBuilder *)clearUninterpretedOption;
+@end
+
+@interface PBEnumValueOptions : PBExtendableMessage {
+@private
+  BOOL hasDeprecated_:1;
+  BOOL deprecated_:1;
+  NSMutableArray * uninterpretedOptionArray;
+}
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+@property (readonly, strong) NSArray * uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+
++ (PBEnumValueOptions*) defaultInstance;
+- (PBEnumValueOptions*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBEnumValueOptionsBuilder*) builder;
++ (PBEnumValueOptionsBuilder*) builder;
++ (PBEnumValueOptionsBuilder*) builderWithPrototype:(PBEnumValueOptions*) prototype;
+- (PBEnumValueOptionsBuilder*) toBuilder;
+
++ (PBEnumValueOptions*) parseFromData:(NSData*) data;
++ (PBEnumValueOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumValueOptions*) parseFromInputStream:(NSInputStream*) input;
++ (PBEnumValueOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBEnumValueOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBEnumValueOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBEnumValueOptionsBuilder : PBExtendableMessageBuilder {
+@private
+  PBEnumValueOptions* result;
+}
+
+- (PBEnumValueOptions*) defaultInstance;
+
+- (PBEnumValueOptionsBuilder*) clear;
+- (PBEnumValueOptionsBuilder*) clone;
+
+- (PBEnumValueOptions*) build;
+- (PBEnumValueOptions*) buildPartial;
+
+- (PBEnumValueOptionsBuilder*) mergeFrom:(PBEnumValueOptions*) other;
+- (PBEnumValueOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBEnumValueOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+- (PBEnumValueOptionsBuilder*) setDeprecated:(BOOL) value;
+- (PBEnumValueOptionsBuilder*) clearDeprecated;
+
+- (NSMutableArray *)uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+- (PBEnumValueOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value;
+- (PBEnumValueOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array;
+- (PBEnumValueOptionsBuilder *)clearUninterpretedOption;
+@end
+
+@interface PBServiceOptions : PBExtendableMessage {
+@private
+  BOOL hasDeprecated_:1;
+  BOOL deprecated_:1;
+  NSMutableArray * uninterpretedOptionArray;
+}
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+@property (readonly, strong) NSArray * uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+
++ (PBServiceOptions*) defaultInstance;
+- (PBServiceOptions*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBServiceOptionsBuilder*) builder;
++ (PBServiceOptionsBuilder*) builder;
++ (PBServiceOptionsBuilder*) builderWithPrototype:(PBServiceOptions*) prototype;
+- (PBServiceOptionsBuilder*) toBuilder;
+
++ (PBServiceOptions*) parseFromData:(NSData*) data;
++ (PBServiceOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBServiceOptions*) parseFromInputStream:(NSInputStream*) input;
++ (PBServiceOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBServiceOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBServiceOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBServiceOptionsBuilder : PBExtendableMessageBuilder {
+@private
+  PBServiceOptions* result;
+}
+
+- (PBServiceOptions*) defaultInstance;
+
+- (PBServiceOptionsBuilder*) clear;
+- (PBServiceOptionsBuilder*) clone;
+
+- (PBServiceOptions*) build;
+- (PBServiceOptions*) buildPartial;
+
+- (PBServiceOptionsBuilder*) mergeFrom:(PBServiceOptions*) other;
+- (PBServiceOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBServiceOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+- (PBServiceOptionsBuilder*) setDeprecated:(BOOL) value;
+- (PBServiceOptionsBuilder*) clearDeprecated;
+
+- (NSMutableArray *)uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+- (PBServiceOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value;
+- (PBServiceOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array;
+- (PBServiceOptionsBuilder *)clearUninterpretedOption;
+@end
+
+@interface PBMethodOptions : PBExtendableMessage {
+@private
+  BOOL hasDeprecated_:1;
+  BOOL deprecated_:1;
+  NSMutableArray * uninterpretedOptionArray;
+}
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+@property (readonly, strong) NSArray * uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+
++ (PBMethodOptions*) defaultInstance;
+- (PBMethodOptions*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBMethodOptionsBuilder*) builder;
++ (PBMethodOptionsBuilder*) builder;
++ (PBMethodOptionsBuilder*) builderWithPrototype:(PBMethodOptions*) prototype;
+- (PBMethodOptionsBuilder*) toBuilder;
+
++ (PBMethodOptions*) parseFromData:(NSData*) data;
++ (PBMethodOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBMethodOptions*) parseFromInputStream:(NSInputStream*) input;
++ (PBMethodOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBMethodOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBMethodOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBMethodOptionsBuilder : PBExtendableMessageBuilder {
+@private
+  PBMethodOptions* result;
+}
+
+- (PBMethodOptions*) defaultInstance;
+
+- (PBMethodOptionsBuilder*) clear;
+- (PBMethodOptionsBuilder*) clone;
+
+- (PBMethodOptions*) build;
+- (PBMethodOptions*) buildPartial;
+
+- (PBMethodOptionsBuilder*) mergeFrom:(PBMethodOptions*) other;
+- (PBMethodOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBMethodOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasDeprecated;
+- (BOOL) deprecated;
+- (PBMethodOptionsBuilder*) setDeprecated:(BOOL) value;
+- (PBMethodOptionsBuilder*) clearDeprecated;
+
+- (NSMutableArray *)uninterpretedOption;
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index;
+- (PBMethodOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value;
+- (PBMethodOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array;
+- (PBMethodOptionsBuilder *)clearUninterpretedOption;
+@end
+
+@interface PBUninterpretedOption : PBGeneratedMessage {
+@private
+  BOOL hasDoubleValue_:1;
+  BOOL hasNegativeIntValue_:1;
+  BOOL hasPositiveIntValue_:1;
+  BOOL hasIdentifierValue_:1;
+  BOOL hasAggregateValue_:1;
+  BOOL hasStringValue_:1;
+  Float64 doubleValue;
+  SInt64 negativeIntValue;
+  UInt64 positiveIntValue;
+  NSString* identifierValue;
+  NSString* aggregateValue;
+  NSData* stringValue;
+  NSMutableArray * nameArray;
+}
+- (BOOL) hasIdentifierValue;
+- (BOOL) hasPositiveIntValue;
+- (BOOL) hasNegativeIntValue;
+- (BOOL) hasDoubleValue;
+- (BOOL) hasStringValue;
+- (BOOL) hasAggregateValue;
+@property (readonly, strong) NSArray * name;
+@property (readonly, strong) NSString* identifierValue;
+@property (readonly) UInt64 positiveIntValue;
+@property (readonly) SInt64 negativeIntValue;
+@property (readonly) Float64 doubleValue;
+@property (readonly, strong) NSData* stringValue;
+@property (readonly, strong) NSString* aggregateValue;
+- (PBUninterpretedOptionNamePart*)nameAtIndex:(NSUInteger)index;
+
++ (PBUninterpretedOption*) defaultInstance;
+- (PBUninterpretedOption*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBUninterpretedOptionBuilder*) builder;
++ (PBUninterpretedOptionBuilder*) builder;
++ (PBUninterpretedOptionBuilder*) builderWithPrototype:(PBUninterpretedOption*) prototype;
+- (PBUninterpretedOptionBuilder*) toBuilder;
+
++ (PBUninterpretedOption*) parseFromData:(NSData*) data;
++ (PBUninterpretedOption*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBUninterpretedOption*) parseFromInputStream:(NSInputStream*) input;
++ (PBUninterpretedOption*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBUninterpretedOption*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBUninterpretedOption*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBUninterpretedOptionNamePart : PBGeneratedMessage {
+@private
+  BOOL hasIsExtension_:1;
+  BOOL hasNamePart_:1;
+  BOOL isExtension_:1;
+  NSString* namePart;
+}
+- (BOOL) hasNamePart;
+- (BOOL) hasIsExtension;
+@property (readonly, strong) NSString* namePart;
+- (BOOL) isExtension;
+
++ (PBUninterpretedOptionNamePart*) defaultInstance;
+- (PBUninterpretedOptionNamePart*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBUninterpretedOptionNamePartBuilder*) builder;
++ (PBUninterpretedOptionNamePartBuilder*) builder;
++ (PBUninterpretedOptionNamePartBuilder*) builderWithPrototype:(PBUninterpretedOptionNamePart*) prototype;
+- (PBUninterpretedOptionNamePartBuilder*) toBuilder;
+
++ (PBUninterpretedOptionNamePart*) parseFromData:(NSData*) data;
++ (PBUninterpretedOptionNamePart*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBUninterpretedOptionNamePart*) parseFromInputStream:(NSInputStream*) input;
++ (PBUninterpretedOptionNamePart*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBUninterpretedOptionNamePart*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBUninterpretedOptionNamePart*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBUninterpretedOptionNamePartBuilder : PBGeneratedMessageBuilder {
+@private
+  PBUninterpretedOptionNamePart* result;
+}
+
+- (PBUninterpretedOptionNamePart*) defaultInstance;
+
+- (PBUninterpretedOptionNamePartBuilder*) clear;
+- (PBUninterpretedOptionNamePartBuilder*) clone;
+
+- (PBUninterpretedOptionNamePart*) build;
+- (PBUninterpretedOptionNamePart*) buildPartial;
+
+- (PBUninterpretedOptionNamePartBuilder*) mergeFrom:(PBUninterpretedOptionNamePart*) other;
+- (PBUninterpretedOptionNamePartBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBUninterpretedOptionNamePartBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (BOOL) hasNamePart;
+- (NSString*) namePart;
+- (PBUninterpretedOptionNamePartBuilder*) setNamePart:(NSString*) value;
+- (PBUninterpretedOptionNamePartBuilder*) clearNamePart;
+
+- (BOOL) hasIsExtension;
+- (BOOL) isExtension;
+- (PBUninterpretedOptionNamePartBuilder*) setIsExtension:(BOOL) value;
+- (PBUninterpretedOptionNamePartBuilder*) clearIsExtension;
+@end
+
+@interface PBUninterpretedOptionBuilder : PBGeneratedMessageBuilder {
+@private
+  PBUninterpretedOption* result;
+}
+
+- (PBUninterpretedOption*) defaultInstance;
+
+- (PBUninterpretedOptionBuilder*) clear;
+- (PBUninterpretedOptionBuilder*) clone;
+
+- (PBUninterpretedOption*) build;
+- (PBUninterpretedOption*) buildPartial;
+
+- (PBUninterpretedOptionBuilder*) mergeFrom:(PBUninterpretedOption*) other;
+- (PBUninterpretedOptionBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBUninterpretedOptionBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (NSMutableArray *)name;
+- (PBUninterpretedOptionNamePart*)nameAtIndex:(NSUInteger)index;
+- (PBUninterpretedOptionBuilder *)addName:(PBUninterpretedOptionNamePart*)value;
+- (PBUninterpretedOptionBuilder *)setNameArray:(NSArray *)array;
+- (PBUninterpretedOptionBuilder *)clearName;
+
+- (BOOL) hasIdentifierValue;
+- (NSString*) identifierValue;
+- (PBUninterpretedOptionBuilder*) setIdentifierValue:(NSString*) value;
+- (PBUninterpretedOptionBuilder*) clearIdentifierValue;
+
+- (BOOL) hasPositiveIntValue;
+- (UInt64) positiveIntValue;
+- (PBUninterpretedOptionBuilder*) setPositiveIntValue:(UInt64) value;
+- (PBUninterpretedOptionBuilder*) clearPositiveIntValue;
+
+- (BOOL) hasNegativeIntValue;
+- (SInt64) negativeIntValue;
+- (PBUninterpretedOptionBuilder*) setNegativeIntValue:(SInt64) value;
+- (PBUninterpretedOptionBuilder*) clearNegativeIntValue;
+
+- (BOOL) hasDoubleValue;
+- (Float64) doubleValue;
+- (PBUninterpretedOptionBuilder*) setDoubleValue:(Float64) value;
+- (PBUninterpretedOptionBuilder*) clearDoubleValue;
+
+- (BOOL) hasStringValue;
+- (NSData*) stringValue;
+- (PBUninterpretedOptionBuilder*) setStringValue:(NSData*) value;
+- (PBUninterpretedOptionBuilder*) clearStringValue;
+
+- (BOOL) hasAggregateValue;
+- (NSString*) aggregateValue;
+- (PBUninterpretedOptionBuilder*) setAggregateValue:(NSString*) value;
+- (PBUninterpretedOptionBuilder*) clearAggregateValue;
+@end
+
+@interface PBSourceCodeInfo : PBGeneratedMessage {
+@private
+  NSMutableArray * locationArray;
+}
+@property (readonly, strong) NSArray * location;
+- (PBSourceCodeInfoLocation*)locationAtIndex:(NSUInteger)index;
+
++ (PBSourceCodeInfo*) defaultInstance;
+- (PBSourceCodeInfo*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBSourceCodeInfoBuilder*) builder;
++ (PBSourceCodeInfoBuilder*) builder;
++ (PBSourceCodeInfoBuilder*) builderWithPrototype:(PBSourceCodeInfo*) prototype;
+- (PBSourceCodeInfoBuilder*) toBuilder;
+
++ (PBSourceCodeInfo*) parseFromData:(NSData*) data;
++ (PBSourceCodeInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBSourceCodeInfo*) parseFromInputStream:(NSInputStream*) input;
++ (PBSourceCodeInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBSourceCodeInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBSourceCodeInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBSourceCodeInfoLocation : PBGeneratedMessage {
+@private
+  BOOL hasLeadingComments_:1;
+  BOOL hasTrailingComments_:1;
+  NSString* leadingComments;
+  NSString* trailingComments;
+  PBAppendableArray * pathArray;
+  SInt32 pathMemoizedSerializedSize;
+  PBAppendableArray * spanArray;
+  SInt32 spanMemoizedSerializedSize;
+}
+- (BOOL) hasLeadingComments;
+- (BOOL) hasTrailingComments;
+@property (readonly, strong) PBArray * path;
+@property (readonly, strong) PBArray * span;
+@property (readonly, strong) NSString* leadingComments;
+@property (readonly, strong) NSString* trailingComments;
+- (SInt32)pathAtIndex:(NSUInteger)index;
+- (SInt32)spanAtIndex:(NSUInteger)index;
+
++ (PBSourceCodeInfoLocation*) defaultInstance;
+- (PBSourceCodeInfoLocation*) defaultInstance;
+
+- (BOOL) isInitialized;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (PBSourceCodeInfoLocationBuilder*) builder;
++ (PBSourceCodeInfoLocationBuilder*) builder;
++ (PBSourceCodeInfoLocationBuilder*) builderWithPrototype:(PBSourceCodeInfoLocation*) prototype;
+- (PBSourceCodeInfoLocationBuilder*) toBuilder;
+
++ (PBSourceCodeInfoLocation*) parseFromData:(NSData*) data;
++ (PBSourceCodeInfoLocation*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBSourceCodeInfoLocation*) parseFromInputStream:(NSInputStream*) input;
++ (PBSourceCodeInfoLocation*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
++ (PBSourceCodeInfoLocation*) parseFromCodedInputStream:(PBCodedInputStream*) input;
++ (PBSourceCodeInfoLocation*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
+
+@interface PBSourceCodeInfoLocationBuilder : PBGeneratedMessageBuilder {
+@private
+  PBSourceCodeInfoLocation* result;
+}
+
+- (PBSourceCodeInfoLocation*) defaultInstance;
+
+- (PBSourceCodeInfoLocationBuilder*) clear;
+- (PBSourceCodeInfoLocationBuilder*) clone;
+
+- (PBSourceCodeInfoLocation*) build;
+- (PBSourceCodeInfoLocation*) buildPartial;
+
+- (PBSourceCodeInfoLocationBuilder*) mergeFrom:(PBSourceCodeInfoLocation*) other;
+- (PBSourceCodeInfoLocationBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBSourceCodeInfoLocationBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (PBAppendableArray *)path;
+- (SInt32)pathAtIndex:(NSUInteger)index;
+- (PBSourceCodeInfoLocationBuilder *)addPath:(SInt32)value;
+- (PBSourceCodeInfoLocationBuilder *)setPathArray:(NSArray *)array;
+- (PBSourceCodeInfoLocationBuilder *)setPathValues:(const SInt32 *)values count:(NSUInteger)count;
+- (PBSourceCodeInfoLocationBuilder *)clearPath;
+
+- (PBAppendableArray *)span;
+- (SInt32)spanAtIndex:(NSUInteger)index;
+- (PBSourceCodeInfoLocationBuilder *)addSpan:(SInt32)value;
+- (PBSourceCodeInfoLocationBuilder *)setSpanArray:(NSArray *)array;
+- (PBSourceCodeInfoLocationBuilder *)setSpanValues:(const SInt32 *)values count:(NSUInteger)count;
+- (PBSourceCodeInfoLocationBuilder *)clearSpan;
+
+- (BOOL) hasLeadingComments;
+- (NSString*) leadingComments;
+- (PBSourceCodeInfoLocationBuilder*) setLeadingComments:(NSString*) value;
+- (PBSourceCodeInfoLocationBuilder*) clearLeadingComments;
+
+- (BOOL) hasTrailingComments;
+- (NSString*) trailingComments;
+- (PBSourceCodeInfoLocationBuilder*) setTrailingComments:(NSString*) value;
+- (PBSourceCodeInfoLocationBuilder*) clearTrailingComments;
+@end
+
+@interface PBSourceCodeInfoBuilder : PBGeneratedMessageBuilder {
+@private
+  PBSourceCodeInfo* result;
+}
+
+- (PBSourceCodeInfo*) defaultInstance;
+
+- (PBSourceCodeInfoBuilder*) clear;
+- (PBSourceCodeInfoBuilder*) clone;
+
+- (PBSourceCodeInfo*) build;
+- (PBSourceCodeInfo*) buildPartial;
+
+- (PBSourceCodeInfoBuilder*) mergeFrom:(PBSourceCodeInfo*) other;
+- (PBSourceCodeInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBSourceCodeInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+- (NSMutableArray *)location;
+- (PBSourceCodeInfoLocation*)locationAtIndex:(NSUInteger)index;
+- (PBSourceCodeInfoBuilder *)addLocation:(PBSourceCodeInfoLocation*)value;
+- (PBSourceCodeInfoBuilder *)setLocationArray:(NSArray *)array;
+- (PBSourceCodeInfoBuilder *)clearLocation;
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/runtime/Classes/Descriptor.pb.m b/src/runtime/Classes/Descriptor.pb.m
new file mode 100755
index 0000000..872bbbc
--- /dev/null
+++ b/src/runtime/Classes/Descriptor.pb.m
@@ -0,0 +1,8515 @@
+// Generated by the protocol buffer compiler.  DO NOT EDIT!
+
+
+#import "Descriptor.pb.h"
+
+// @@protoc_insertion_point(imports)
+
+@implementation PBDescriptorRoot
+static PBExtensionRegistry* extensionRegistry = nil;
++ (PBExtensionRegistry*) extensionRegistry {
+  return extensionRegistry;
+}
+
++ (void) initialize {
+  if (self == [PBDescriptorRoot class]) {
+    PBMutableExtensionRegistry* registry = [PBMutableExtensionRegistry registry];
+    [self registerAllExtensions:registry];
+    extensionRegistry = registry;
+  }
+}
++ (void) registerAllExtensions:(PBMutableExtensionRegistry*) registry {
+}
+@end
+
+@interface PBFileDescriptorSet ()
+@property (strong) NSMutableArray * fileArray;
+@end
+
+@implementation PBFileDescriptorSet
+
+@synthesize fileArray;
+@dynamic file;
+- (id) init {
+  if ((self = [super init])) {
+  }
+  return self;
+}
+static PBFileDescriptorSet* defaultPBFileDescriptorSetInstance = nil;
++ (void) initialize {
+  if (self == [PBFileDescriptorSet class]) {
+    defaultPBFileDescriptorSetInstance = [[PBFileDescriptorSet alloc] init];
+  }
+}
++ (PBFileDescriptorSet*) defaultInstance {
+  return defaultPBFileDescriptorSetInstance;
+}
+- (PBFileDescriptorSet*) defaultInstance {
+  return defaultPBFileDescriptorSetInstance;
+}
+- (NSArray *)file {
+  return fileArray;
+}
+- (PBFileDescriptorProto*)fileAtIndex:(NSUInteger)index {
+  return [fileArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInitfile = YES;
+   [self.file enumerateObjectsUsingBlock:^(PBFileDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitfile = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitfile) return isInitfile;
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  [self.fileArray enumerateObjectsUsingBlock:^(PBFileDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:1 value:element];
+  }];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  [self.fileArray enumerateObjectsUsingBlock:^(PBFileDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(1, element);
+  }];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBFileDescriptorSet*) parseFromData:(NSData*) data {
+  return (PBFileDescriptorSet*)[[[PBFileDescriptorSet builder] mergeFromData:data] build];
+}
++ (PBFileDescriptorSet*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileDescriptorSet*)[[[PBFileDescriptorSet builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBFileDescriptorSet*) parseFromInputStream:(NSInputStream*) input {
+  return (PBFileDescriptorSet*)[[[PBFileDescriptorSet builder] mergeFromInputStream:input] build];
+}
++ (PBFileDescriptorSet*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileDescriptorSet*)[[[PBFileDescriptorSet builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFileDescriptorSet*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBFileDescriptorSet*)[[[PBFileDescriptorSet builder] mergeFromCodedInputStream:input] build];
+}
++ (PBFileDescriptorSet*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileDescriptorSet*)[[[PBFileDescriptorSet builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFileDescriptorSetBuilder*) builder {
+  return [[PBFileDescriptorSetBuilder alloc] init];
+}
++ (PBFileDescriptorSetBuilder*) builderWithPrototype:(PBFileDescriptorSet*) prototype {
+  return [[PBFileDescriptorSet builder] mergeFrom:prototype];
+}
+- (PBFileDescriptorSetBuilder*) builder {
+  return [PBFileDescriptorSet builder];
+}
+- (PBFileDescriptorSetBuilder*) toBuilder {
+  return [PBFileDescriptorSet builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.fileArray enumerateObjectsUsingBlock:^(PBFileDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"file"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBFileDescriptorSet class]]) {
+    return NO;
+  }
+  PBFileDescriptorSet *otherMessage = other;
+  return
+      [self.fileArray isEqualToArray:otherMessage.fileArray] &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  [self.fileArray enumerateObjectsUsingBlock:^(PBFileDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBFileDescriptorSetBuilder()
+@property (strong) PBFileDescriptorSet* result;
+@end
+
+@implementation PBFileDescriptorSetBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBFileDescriptorSet alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBFileDescriptorSetBuilder*) clear {
+  self.result = [[PBFileDescriptorSet alloc] init];
+  return self;
+}
+- (PBFileDescriptorSetBuilder*) clone {
+  return [PBFileDescriptorSet builderWithPrototype:result];
+}
+- (PBFileDescriptorSet*) defaultInstance {
+  return [PBFileDescriptorSet defaultInstance];
+}
+- (PBFileDescriptorSet*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBFileDescriptorSet*) buildPartial {
+  PBFileDescriptorSet* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBFileDescriptorSetBuilder*) mergeFrom:(PBFileDescriptorSet*) other {
+  if (other == [PBFileDescriptorSet defaultInstance]) {
+    return self;
+  }
+  if (other.fileArray.count > 0) {
+    if (result.fileArray == nil) {
+      result.fileArray = [[NSMutableArray alloc] initWithArray:other.fileArray];
+    } else {
+      [result.fileArray addObjectsFromArray:other.fileArray];
+    }
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBFileDescriptorSetBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBFileDescriptorSetBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        PBFileDescriptorProtoBuilder* subBuilder = [PBFileDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addFile:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (NSMutableArray *)file {
+  return result.fileArray;
+}
+- (PBFileDescriptorProto*)fileAtIndex:(NSUInteger)index {
+  return [result fileAtIndex:index];
+}
+- (PBFileDescriptorSetBuilder *)addFile:(PBFileDescriptorProto*)value {
+  if (result.fileArray == nil) {
+    result.fileArray = [[NSMutableArray alloc]init];
+  }
+  [result.fileArray addObject:value];
+  return self;
+}
+- (PBFileDescriptorSetBuilder *)setFileArray:(NSArray *)array {
+  result.fileArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBFileDescriptorSetBuilder *)clearFile {
+  result.fileArray = nil;
+  return self;
+}
+@end
+
+@interface PBFileDescriptorProto ()
+@property (strong) NSString* name;
+@property (strong) NSString* package;
+@property (strong) NSMutableArray * dependencyArray;
+@property (strong) PBAppendableArray * publicDependencyArray;
+@property (strong) PBAppendableArray * weakDependencyArray;
+@property (strong) NSMutableArray * messageTypeArray;
+@property (strong) NSMutableArray * enumTypeArray;
+@property (strong) NSMutableArray * serviceArray;
+@property (strong) NSMutableArray * extensionArray;
+@property (strong) PBFileOptions* options;
+@property (strong) PBSourceCodeInfo* sourceCodeInfo;
+@end
+
+@implementation PBFileDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+- (BOOL) hasPackage {
+  return !!hasPackage_;
+}
+- (void) setHasPackage:(BOOL) value_ {
+  hasPackage_ = !!value_;
+}
+@synthesize package;
+@synthesize dependencyArray;
+@dynamic dependency;
+@synthesize publicDependencyArray;
+@dynamic publicDependency;
+@synthesize weakDependencyArray;
+@dynamic weakDependency;
+@synthesize messageTypeArray;
+@dynamic messageType;
+@synthesize enumTypeArray;
+@dynamic enumType;
+@synthesize serviceArray;
+@dynamic service;
+@synthesize extensionArray;
+@dynamic extension;
+- (BOOL) hasOptions {
+  return !!hasOptions_;
+}
+- (void) setHasOptions:(BOOL) value_ {
+  hasOptions_ = !!value_;
+}
+@synthesize options;
+- (BOOL) hasSourceCodeInfo {
+  return !!hasSourceCodeInfo_;
+}
+- (void) setHasSourceCodeInfo:(BOOL) value_ {
+  hasSourceCodeInfo_ = !!value_;
+}
+@synthesize sourceCodeInfo;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+    self.package = @"";
+    self.options = [PBFileOptions defaultInstance];
+    self.sourceCodeInfo = [PBSourceCodeInfo defaultInstance];
+  }
+  return self;
+}
+static PBFileDescriptorProto* defaultPBFileDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBFileDescriptorProto class]) {
+    defaultPBFileDescriptorProtoInstance = [[PBFileDescriptorProto alloc] init];
+  }
+}
++ (PBFileDescriptorProto*) defaultInstance {
+  return defaultPBFileDescriptorProtoInstance;
+}
+- (PBFileDescriptorProto*) defaultInstance {
+  return defaultPBFileDescriptorProtoInstance;
+}
+- (NSArray *)dependency {
+  return dependencyArray;
+}
+- (NSString*)dependencyAtIndex:(NSUInteger)index {
+  return [dependencyArray objectAtIndex:index];
+}
+- (PBArray *)publicDependency {
+  return publicDependencyArray;
+}
+- (SInt32)publicDependencyAtIndex:(NSUInteger)index {
+  return [publicDependencyArray int32AtIndex:index];
+}
+- (PBArray *)weakDependency {
+  return weakDependencyArray;
+}
+- (SInt32)weakDependencyAtIndex:(NSUInteger)index {
+  return [weakDependencyArray int32AtIndex:index];
+}
+- (NSArray *)messageType {
+  return messageTypeArray;
+}
+- (PBDescriptorProto*)messageTypeAtIndex:(NSUInteger)index {
+  return [messageTypeArray objectAtIndex:index];
+}
+- (NSArray *)enumType {
+  return enumTypeArray;
+}
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index {
+  return [enumTypeArray objectAtIndex:index];
+}
+- (NSArray *)service {
+  return serviceArray;
+}
+- (PBServiceDescriptorProto*)serviceAtIndex:(NSUInteger)index {
+  return [serviceArray objectAtIndex:index];
+}
+- (NSArray *)extension {
+  return extensionArray;
+}
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index {
+  return [extensionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInitmessageType = YES;
+   [self.messageType enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitmessageType = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitmessageType) return isInitmessageType;
+  __block BOOL isInitenumType = YES;
+   [self.enumType enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitenumType = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitenumType) return isInitenumType;
+  __block BOOL isInitservice = YES;
+   [self.service enumerateObjectsUsingBlock:^(PBServiceDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitservice = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitservice) return isInitservice;
+  __block BOOL isInitextension = YES;
+   [self.extension enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitextension = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitextension) return isInitextension;
+  if (self.hasOptions) {
+    if (!self.options.isInitialized) {
+      return NO;
+    }
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  if (self.hasPackage) {
+    [output writeString:2 value:self.package];
+  }
+  [self.dependencyArray enumerateObjectsUsingBlock:^(NSString *element, NSUInteger idx, BOOL *stop) {
+    [output writeString:3 value:element];
+  }];
+  [self.messageTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:4 value:element];
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:5 value:element];
+  }];
+  [self.serviceArray enumerateObjectsUsingBlock:^(PBServiceDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:6 value:element];
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:7 value:element];
+  }];
+  if (self.hasOptions) {
+    [output writeMessage:8 value:self.options];
+  }
+  if (self.hasSourceCodeInfo) {
+    [output writeMessage:9 value:self.sourceCodeInfo];
+  }
+  const NSUInteger publicDependencyArrayCount = self.publicDependencyArray.count;
+  if (publicDependencyArrayCount > 0) {
+    const SInt32 *values = (const SInt32 *)self.publicDependencyArray.data;
+    for (NSUInteger i = 0; i < publicDependencyArrayCount; ++i) {
+      [output writeInt32:10 value:values[i]];
+    }
+  }
+  const NSUInteger weakDependencyArrayCount = self.weakDependencyArray.count;
+  if (weakDependencyArrayCount > 0) {
+    const SInt32 *values = (const SInt32 *)self.weakDependencyArray.data;
+    for (NSUInteger i = 0; i < weakDependencyArrayCount; ++i) {
+      [output writeInt32:11 value:values[i]];
+    }
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  if (self.hasPackage) {
+    size_ += computeStringSize(2, self.package);
+  }
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.dependencyArray.count;
+    [self.dependencyArray enumerateObjectsUsingBlock:^(NSString *element, NSUInteger idx, BOOL *stop) {
+      dataSize += computeStringSizeNoTag(element);
+    }];
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  [self.messageTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(4, element);
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(5, element);
+  }];
+  [self.serviceArray enumerateObjectsUsingBlock:^(PBServiceDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(6, element);
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(7, element);
+  }];
+  if (self.hasOptions) {
+    size_ += computeMessageSize(8, self.options);
+  }
+  if (self.hasSourceCodeInfo) {
+    size_ += computeMessageSize(9, self.sourceCodeInfo);
+  }
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.publicDependencyArray.count;
+    const SInt32 *values = (const SInt32 *)self.publicDependencyArray.data;
+    for (NSUInteger i = 0; i < count; ++i) {
+      dataSize += computeInt32SizeNoTag(values[i]);
+    }
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.weakDependencyArray.count;
+    const SInt32 *values = (const SInt32 *)self.weakDependencyArray.data;
+    for (NSUInteger i = 0; i < count; ++i) {
+      dataSize += computeInt32SizeNoTag(values[i]);
+    }
+    size_ += dataSize;
+    size_ += (SInt32)(1 * count);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBFileDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBFileDescriptorProto*)[[[PBFileDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBFileDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileDescriptorProto*)[[[PBFileDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBFileDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBFileDescriptorProto*)[[[PBFileDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBFileDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileDescriptorProto*)[[[PBFileDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFileDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBFileDescriptorProto*)[[[PBFileDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBFileDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileDescriptorProto*)[[[PBFileDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFileDescriptorProtoBuilder*) builder {
+  return [[PBFileDescriptorProtoBuilder alloc] init];
+}
++ (PBFileDescriptorProtoBuilder*) builderWithPrototype:(PBFileDescriptorProto*) prototype {
+  return [[PBFileDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBFileDescriptorProtoBuilder*) builder {
+  return [PBFileDescriptorProto builder];
+}
+- (PBFileDescriptorProtoBuilder*) toBuilder {
+  return [PBFileDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  if (self.hasPackage) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"package", self.package];
+  }
+  [self.dependencyArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"dependency", obj];
+  }];
+  [self.messageTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"messageType"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"enumType"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.serviceArray enumerateObjectsUsingBlock:^(PBServiceDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"service"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"extension"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasOptions) {
+    [output appendFormat:@"%@%@ {\n", indent, @"options"];
+    [self.options writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasSourceCodeInfo) {
+    [output appendFormat:@"%@%@ {\n", indent, @"sourceCodeInfo"];
+    [self.sourceCodeInfo writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.publicDependencyArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"publicDependency", obj];
+  }];
+  [self.weakDependencyArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"weakDependency", obj];
+  }];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBFileDescriptorProto class]]) {
+    return NO;
+  }
+  PBFileDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      self.hasPackage == otherMessage.hasPackage &&
+      (!self.hasPackage || [self.package isEqual:otherMessage.package]) &&
+      [self.dependencyArray isEqualToArray:otherMessage.dependencyArray] &&
+      [self.messageTypeArray isEqualToArray:otherMessage.messageTypeArray] &&
+      [self.enumTypeArray isEqualToArray:otherMessage.enumTypeArray] &&
+      [self.serviceArray isEqualToArray:otherMessage.serviceArray] &&
+      [self.extensionArray isEqualToArray:otherMessage.extensionArray] &&
+      self.hasOptions == otherMessage.hasOptions &&
+      (!self.hasOptions || [self.options isEqual:otherMessage.options]) &&
+      self.hasSourceCodeInfo == otherMessage.hasSourceCodeInfo &&
+      (!self.hasSourceCodeInfo || [self.sourceCodeInfo isEqual:otherMessage.sourceCodeInfo]) &&
+      [self.publicDependencyArray isEqualToArray:otherMessage.publicDependencyArray] &&
+      [self.weakDependencyArray isEqualToArray:otherMessage.weakDependencyArray] &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  if (self.hasPackage) {
+    hashCode = hashCode * 31 + [self.package hash];
+  }
+  [self.dependencyArray enumerateObjectsUsingBlock:^(id element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.messageTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.serviceArray enumerateObjectsUsingBlock:^(PBServiceDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasOptions) {
+    hashCode = hashCode * 31 + [self.options hash];
+  }
+  if (self.hasSourceCodeInfo) {
+    hashCode = hashCode * 31 + [self.sourceCodeInfo hash];
+  }
+  [self.publicDependencyArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [obj longValue];
+  }];
+  [self.weakDependencyArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [obj longValue];
+  }];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBFileDescriptorProtoBuilder()
+@property (strong) PBFileDescriptorProto* result;
+@end
+
+@implementation PBFileDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBFileDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBFileDescriptorProtoBuilder*) clear {
+  self.result = [[PBFileDescriptorProto alloc] init];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) clone {
+  return [PBFileDescriptorProto builderWithPrototype:result];
+}
+- (PBFileDescriptorProto*) defaultInstance {
+  return [PBFileDescriptorProto defaultInstance];
+}
+- (PBFileDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBFileDescriptorProto*) buildPartial {
+  PBFileDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBFileDescriptorProtoBuilder*) mergeFrom:(PBFileDescriptorProto*) other {
+  if (other == [PBFileDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  if (other.hasPackage) {
+    [self setPackage:other.package];
+  }
+  if (other.dependencyArray.count > 0) {
+    if (result.dependencyArray == nil) {
+      result.dependencyArray = [[NSMutableArray alloc] initWithArray:other.dependencyArray];
+    } else {
+      [result.dependencyArray addObjectsFromArray:other.dependencyArray];
+    }
+  }
+  if (other.publicDependencyArray.count > 0) {
+    if (result.publicDependencyArray == nil) {
+      result.publicDependencyArray = [other.publicDependencyArray copy];
+    } else {
+      [result.publicDependencyArray appendArray:other.publicDependencyArray];
+    }
+  }
+  if (other.weakDependencyArray.count > 0) {
+    if (result.weakDependencyArray == nil) {
+      result.weakDependencyArray = [other.weakDependencyArray copy];
+    } else {
+      [result.weakDependencyArray appendArray:other.weakDependencyArray];
+    }
+  }
+  if (other.messageTypeArray.count > 0) {
+    if (result.messageTypeArray == nil) {
+      result.messageTypeArray = [[NSMutableArray alloc] initWithArray:other.messageTypeArray];
+    } else {
+      [result.messageTypeArray addObjectsFromArray:other.messageTypeArray];
+    }
+  }
+  if (other.enumTypeArray.count > 0) {
+    if (result.enumTypeArray == nil) {
+      result.enumTypeArray = [[NSMutableArray alloc] initWithArray:other.enumTypeArray];
+    } else {
+      [result.enumTypeArray addObjectsFromArray:other.enumTypeArray];
+    }
+  }
+  if (other.serviceArray.count > 0) {
+    if (result.serviceArray == nil) {
+      result.serviceArray = [[NSMutableArray alloc] initWithArray:other.serviceArray];
+    } else {
+      [result.serviceArray addObjectsFromArray:other.serviceArray];
+    }
+  }
+  if (other.extensionArray.count > 0) {
+    if (result.extensionArray == nil) {
+      result.extensionArray = [[NSMutableArray alloc] initWithArray:other.extensionArray];
+    } else {
+      [result.extensionArray addObjectsFromArray:other.extensionArray];
+    }
+  }
+  if (other.hasOptions) {
+    [self mergeOptions:other.options];
+  }
+  if (other.hasSourceCodeInfo) {
+    [self mergeSourceCodeInfo:other.sourceCodeInfo];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBFileDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+      case 18: {
+        [self setPackage:[input readString]];
+        break;
+      }
+      case 26: {
+        [self addDependency:[input readString]];
+        break;
+      }
+      case 34: {
+        PBDescriptorProtoBuilder* subBuilder = [PBDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addMessageType:[subBuilder buildPartial]];
+        break;
+      }
+      case 42: {
+        PBEnumDescriptorProtoBuilder* subBuilder = [PBEnumDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addEnumType:[subBuilder buildPartial]];
+        break;
+      }
+      case 50: {
+        PBServiceDescriptorProtoBuilder* subBuilder = [PBServiceDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addService:[subBuilder buildPartial]];
+        break;
+      }
+      case 58: {
+        PBFieldDescriptorProtoBuilder* subBuilder = [PBFieldDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addExtension:[subBuilder buildPartial]];
+        break;
+      }
+      case 66: {
+        PBFileOptionsBuilder* subBuilder = [PBFileOptions builder];
+        if (self.hasOptions) {
+          [subBuilder mergeFrom:self.options];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setOptions:[subBuilder buildPartial]];
+        break;
+      }
+      case 74: {
+        PBSourceCodeInfoBuilder* subBuilder = [PBSourceCodeInfo builder];
+        if (self.hasSourceCodeInfo) {
+          [subBuilder mergeFrom:self.sourceCodeInfo];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setSourceCodeInfo:[subBuilder buildPartial]];
+        break;
+      }
+      case 80: {
+        [self addPublicDependency:[input readInt32]];
+        break;
+      }
+      case 88: {
+        [self addWeakDependency:[input readInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBFileDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+- (BOOL) hasPackage {
+  return result.hasPackage;
+}
+- (NSString*) package {
+  return result.package;
+}
+- (PBFileDescriptorProtoBuilder*) setPackage:(NSString*) value {
+  result.hasPackage = YES;
+  result.package = value;
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) clearPackage {
+  result.hasPackage = NO;
+  result.package = @"";
+  return self;
+}
+- (NSMutableArray *)dependency {
+  return result.dependencyArray;
+}
+- (NSString*)dependencyAtIndex:(NSUInteger)index {
+  return [result dependencyAtIndex:index];
+}
+- (PBFileDescriptorProtoBuilder *)addDependency:(NSString*)value {
+  if (result.dependencyArray == nil) {
+    result.dependencyArray = [[NSMutableArray alloc]init];
+  }
+  [result.dependencyArray addObject:value];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setDependencyArray:(NSArray *)array {
+  result.dependencyArray = [[NSMutableArray alloc] initWithArray:array];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)clearDependency {
+  result.dependencyArray = nil;
+  return self;
+}
+- (PBAppendableArray *)publicDependency {
+  return result.publicDependencyArray;
+}
+- (SInt32)publicDependencyAtIndex:(NSUInteger)index {
+  return [result publicDependencyAtIndex:index];
+}
+- (PBFileDescriptorProtoBuilder *)addPublicDependency:(SInt32)value {
+  if (result.publicDependencyArray == nil) {
+    result.publicDependencyArray = [PBAppendableArray arrayWithValueType:PBArrayValueTypeInt32];
+  }
+  [result.publicDependencyArray addInt32:value];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setPublicDependencyArray:(NSArray *)array {
+  result.publicDependencyArray = [PBAppendableArray arrayWithArray:array valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setPublicDependencyValues:(const SInt32 *)values count:(NSUInteger)count {
+  result.publicDependencyArray = [PBAppendableArray arrayWithValues:values count:count valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)clearPublicDependency {
+  result.publicDependencyArray = nil;
+  return self;
+}
+- (PBAppendableArray *)weakDependency {
+  return result.weakDependencyArray;
+}
+- (SInt32)weakDependencyAtIndex:(NSUInteger)index {
+  return [result weakDependencyAtIndex:index];
+}
+- (PBFileDescriptorProtoBuilder *)addWeakDependency:(SInt32)value {
+  if (result.weakDependencyArray == nil) {
+    result.weakDependencyArray = [PBAppendableArray arrayWithValueType:PBArrayValueTypeInt32];
+  }
+  [result.weakDependencyArray addInt32:value];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setWeakDependencyArray:(NSArray *)array {
+  result.weakDependencyArray = [PBAppendableArray arrayWithArray:array valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setWeakDependencyValues:(const SInt32 *)values count:(NSUInteger)count {
+  result.weakDependencyArray = [PBAppendableArray arrayWithValues:values count:count valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)clearWeakDependency {
+  result.weakDependencyArray = nil;
+  return self;
+}
+- (NSMutableArray *)messageType {
+  return result.messageTypeArray;
+}
+- (PBDescriptorProto*)messageTypeAtIndex:(NSUInteger)index {
+  return [result messageTypeAtIndex:index];
+}
+- (PBFileDescriptorProtoBuilder *)addMessageType:(PBDescriptorProto*)value {
+  if (result.messageTypeArray == nil) {
+    result.messageTypeArray = [[NSMutableArray alloc]init];
+  }
+  [result.messageTypeArray addObject:value];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setMessageTypeArray:(NSArray *)array {
+  result.messageTypeArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)clearMessageType {
+  result.messageTypeArray = nil;
+  return self;
+}
+- (NSMutableArray *)enumType {
+  return result.enumTypeArray;
+}
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index {
+  return [result enumTypeAtIndex:index];
+}
+- (PBFileDescriptorProtoBuilder *)addEnumType:(PBEnumDescriptorProto*)value {
+  if (result.enumTypeArray == nil) {
+    result.enumTypeArray = [[NSMutableArray alloc]init];
+  }
+  [result.enumTypeArray addObject:value];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setEnumTypeArray:(NSArray *)array {
+  result.enumTypeArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)clearEnumType {
+  result.enumTypeArray = nil;
+  return self;
+}
+- (NSMutableArray *)service {
+  return result.serviceArray;
+}
+- (PBServiceDescriptorProto*)serviceAtIndex:(NSUInteger)index {
+  return [result serviceAtIndex:index];
+}
+- (PBFileDescriptorProtoBuilder *)addService:(PBServiceDescriptorProto*)value {
+  if (result.serviceArray == nil) {
+    result.serviceArray = [[NSMutableArray alloc]init];
+  }
+  [result.serviceArray addObject:value];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setServiceArray:(NSArray *)array {
+  result.serviceArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)clearService {
+  result.serviceArray = nil;
+  return self;
+}
+- (NSMutableArray *)extension {
+  return result.extensionArray;
+}
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index {
+  return [result extensionAtIndex:index];
+}
+- (PBFileDescriptorProtoBuilder *)addExtension:(PBFieldDescriptorProto*)value {
+  if (result.extensionArray == nil) {
+    result.extensionArray = [[NSMutableArray alloc]init];
+  }
+  [result.extensionArray addObject:value];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)setExtensionArray:(NSArray *)array {
+  result.extensionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBFileDescriptorProtoBuilder *)clearExtension {
+  result.extensionArray = nil;
+  return self;
+}
+- (BOOL) hasOptions {
+  return result.hasOptions;
+}
+- (PBFileOptions*) options {
+  return result.options;
+}
+- (PBFileDescriptorProtoBuilder*) setOptions:(PBFileOptions*) value {
+  result.hasOptions = YES;
+  result.options = value;
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) setOptionsBuilder:(PBFileOptionsBuilder*) builderForValue {
+  return [self setOptions:[builderForValue build]];
+}
+- (PBFileDescriptorProtoBuilder*) mergeOptions:(PBFileOptions*) value {
+  if (result.hasOptions &&
+      result.options != [PBFileOptions defaultInstance]) {
+    result.options =
+      [[[PBFileOptions builderWithPrototype:result.options] mergeFrom:value] buildPartial];
+  } else {
+    result.options = value;
+  }
+  result.hasOptions = YES;
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) clearOptions {
+  result.hasOptions = NO;
+  result.options = [PBFileOptions defaultInstance];
+  return self;
+}
+- (BOOL) hasSourceCodeInfo {
+  return result.hasSourceCodeInfo;
+}
+- (PBSourceCodeInfo*) sourceCodeInfo {
+  return result.sourceCodeInfo;
+}
+- (PBFileDescriptorProtoBuilder*) setSourceCodeInfo:(PBSourceCodeInfo*) value {
+  result.hasSourceCodeInfo = YES;
+  result.sourceCodeInfo = value;
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) setSourceCodeInfoBuilder:(PBSourceCodeInfoBuilder*) builderForValue {
+  return [self setSourceCodeInfo:[builderForValue build]];
+}
+- (PBFileDescriptorProtoBuilder*) mergeSourceCodeInfo:(PBSourceCodeInfo*) value {
+  if (result.hasSourceCodeInfo &&
+      result.sourceCodeInfo != [PBSourceCodeInfo defaultInstance]) {
+    result.sourceCodeInfo =
+      [[[PBSourceCodeInfo builderWithPrototype:result.sourceCodeInfo] mergeFrom:value] buildPartial];
+  } else {
+    result.sourceCodeInfo = value;
+  }
+  result.hasSourceCodeInfo = YES;
+  return self;
+}
+- (PBFileDescriptorProtoBuilder*) clearSourceCodeInfo {
+  result.hasSourceCodeInfo = NO;
+  result.sourceCodeInfo = [PBSourceCodeInfo defaultInstance];
+  return self;
+}
+@end
+
+@interface PBDescriptorProto ()
+@property (strong) NSString* name;
+@property (strong) NSMutableArray * fieldArray;
+@property (strong) NSMutableArray * extensionArray;
+@property (strong) NSMutableArray * nestedTypeArray;
+@property (strong) NSMutableArray * enumTypeArray;
+@property (strong) NSMutableArray * extensionRangeArray;
+@property (strong) NSMutableArray * oneofDeclArray;
+@property (strong) PBMessageOptions* options;
+@end
+
+@implementation PBDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+@synthesize fieldArray;
+@dynamic field;
+@synthesize extensionArray;
+@dynamic extension;
+@synthesize nestedTypeArray;
+@dynamic nestedType;
+@synthesize enumTypeArray;
+@dynamic enumType;
+@synthesize extensionRangeArray;
+@dynamic extensionRange;
+@synthesize oneofDeclArray;
+@dynamic oneofDecl;
+- (BOOL) hasOptions {
+  return !!hasOptions_;
+}
+- (void) setHasOptions:(BOOL) value_ {
+  hasOptions_ = !!value_;
+}
+@synthesize options;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+    self.options = [PBMessageOptions defaultInstance];
+  }
+  return self;
+}
+static PBDescriptorProto* defaultPBDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBDescriptorProto class]) {
+    defaultPBDescriptorProtoInstance = [[PBDescriptorProto alloc] init];
+  }
+}
++ (PBDescriptorProto*) defaultInstance {
+  return defaultPBDescriptorProtoInstance;
+}
+- (PBDescriptorProto*) defaultInstance {
+  return defaultPBDescriptorProtoInstance;
+}
+- (NSArray *)field {
+  return fieldArray;
+}
+- (PBFieldDescriptorProto*)fieldAtIndex:(NSUInteger)index {
+  return [fieldArray objectAtIndex:index];
+}
+- (NSArray *)extension {
+  return extensionArray;
+}
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index {
+  return [extensionArray objectAtIndex:index];
+}
+- (NSArray *)nestedType {
+  return nestedTypeArray;
+}
+- (PBDescriptorProto*)nestedTypeAtIndex:(NSUInteger)index {
+  return [nestedTypeArray objectAtIndex:index];
+}
+- (NSArray *)enumType {
+  return enumTypeArray;
+}
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index {
+  return [enumTypeArray objectAtIndex:index];
+}
+- (NSArray *)extensionRange {
+  return extensionRangeArray;
+}
+- (PBDescriptorProtoExtensionRange*)extensionRangeAtIndex:(NSUInteger)index {
+  return [extensionRangeArray objectAtIndex:index];
+}
+- (NSArray *)oneofDecl {
+  return oneofDeclArray;
+}
+- (PBOneofDescriptorProto*)oneofDeclAtIndex:(NSUInteger)index {
+  return [oneofDeclArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInitfield = YES;
+   [self.field enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitfield = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitfield) return isInitfield;
+  __block BOOL isInitextension = YES;
+   [self.extension enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitextension = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitextension) return isInitextension;
+  __block BOOL isInitnestedType = YES;
+   [self.nestedType enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitnestedType = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitnestedType) return isInitnestedType;
+  __block BOOL isInitenumType = YES;
+   [self.enumType enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitenumType = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitenumType) return isInitenumType;
+  if (self.hasOptions) {
+    if (!self.options.isInitialized) {
+      return NO;
+    }
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  [self.fieldArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:2 value:element];
+  }];
+  [self.nestedTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:3 value:element];
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:4 value:element];
+  }];
+  [self.extensionRangeArray enumerateObjectsUsingBlock:^(PBDescriptorProtoExtensionRange *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:5 value:element];
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:6 value:element];
+  }];
+  if (self.hasOptions) {
+    [output writeMessage:7 value:self.options];
+  }
+  [self.oneofDeclArray enumerateObjectsUsingBlock:^(PBOneofDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:8 value:element];
+  }];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  [self.fieldArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(2, element);
+  }];
+  [self.nestedTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(3, element);
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(4, element);
+  }];
+  [self.extensionRangeArray enumerateObjectsUsingBlock:^(PBDescriptorProtoExtensionRange *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(5, element);
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(6, element);
+  }];
+  if (self.hasOptions) {
+    size_ += computeMessageSize(7, self.options);
+  }
+  [self.oneofDeclArray enumerateObjectsUsingBlock:^(PBOneofDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(8, element);
+  }];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBDescriptorProto*)[[[PBDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBDescriptorProto*)[[[PBDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBDescriptorProto*)[[[PBDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBDescriptorProto*)[[[PBDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBDescriptorProto*)[[[PBDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBDescriptorProto*)[[[PBDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBDescriptorProtoBuilder*) builder {
+  return [[PBDescriptorProtoBuilder alloc] init];
+}
++ (PBDescriptorProtoBuilder*) builderWithPrototype:(PBDescriptorProto*) prototype {
+  return [[PBDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBDescriptorProtoBuilder*) builder {
+  return [PBDescriptorProto builder];
+}
+- (PBDescriptorProtoBuilder*) toBuilder {
+  return [PBDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  [self.fieldArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"field"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.nestedTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"nestedType"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"enumType"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.extensionRangeArray enumerateObjectsUsingBlock:^(PBDescriptorProtoExtensionRange *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"extensionRange"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"extension"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasOptions) {
+    [output appendFormat:@"%@%@ {\n", indent, @"options"];
+    [self.options writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.oneofDeclArray enumerateObjectsUsingBlock:^(PBOneofDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"oneofDecl"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBDescriptorProto class]]) {
+    return NO;
+  }
+  PBDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      [self.fieldArray isEqualToArray:otherMessage.fieldArray] &&
+      [self.nestedTypeArray isEqualToArray:otherMessage.nestedTypeArray] &&
+      [self.enumTypeArray isEqualToArray:otherMessage.enumTypeArray] &&
+      [self.extensionRangeArray isEqualToArray:otherMessage.extensionRangeArray] &&
+      [self.extensionArray isEqualToArray:otherMessage.extensionArray] &&
+      self.hasOptions == otherMessage.hasOptions &&
+      (!self.hasOptions || [self.options isEqual:otherMessage.options]) &&
+      [self.oneofDeclArray isEqualToArray:otherMessage.oneofDeclArray] &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  [self.fieldArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.nestedTypeArray enumerateObjectsUsingBlock:^(PBDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.enumTypeArray enumerateObjectsUsingBlock:^(PBEnumDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.extensionRangeArray enumerateObjectsUsingBlock:^(PBDescriptorProtoExtensionRange *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  [self.extensionArray enumerateObjectsUsingBlock:^(PBFieldDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasOptions) {
+    hashCode = hashCode * 31 + [self.options hash];
+  }
+  [self.oneofDeclArray enumerateObjectsUsingBlock:^(PBOneofDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBDescriptorProtoExtensionRange ()
+@property SInt32 start;
+@property SInt32 end;
+@end
+
+@implementation PBDescriptorProtoExtensionRange
+
+- (BOOL) hasStart {
+  return !!hasStart_;
+}
+- (void) setHasStart:(BOOL) value_ {
+  hasStart_ = !!value_;
+}
+@synthesize start;
+- (BOOL) hasEnd {
+  return !!hasEnd_;
+}
+- (void) setHasEnd:(BOOL) value_ {
+  hasEnd_ = !!value_;
+}
+@synthesize end;
+- (id) init {
+  if ((self = [super init])) {
+    self.start = 0;
+    self.end = 0;
+  }
+  return self;
+}
+static PBDescriptorProtoExtensionRange* defaultPBDescriptorProtoExtensionRangeInstance = nil;
++ (void) initialize {
+  if (self == [PBDescriptorProtoExtensionRange class]) {
+    defaultPBDescriptorProtoExtensionRangeInstance = [[PBDescriptorProtoExtensionRange alloc] init];
+  }
+}
++ (PBDescriptorProtoExtensionRange*) defaultInstance {
+  return defaultPBDescriptorProtoExtensionRangeInstance;
+}
+- (PBDescriptorProtoExtensionRange*) defaultInstance {
+  return defaultPBDescriptorProtoExtensionRangeInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasStart) {
+    [output writeInt32:1 value:self.start];
+  }
+  if (self.hasEnd) {
+    [output writeInt32:2 value:self.end];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasStart) {
+    size_ += computeInt32Size(1, self.start);
+  }
+  if (self.hasEnd) {
+    size_ += computeInt32Size(2, self.end);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBDescriptorProtoExtensionRange*) parseFromData:(NSData*) data {
+  return (PBDescriptorProtoExtensionRange*)[[[PBDescriptorProtoExtensionRange builder] mergeFromData:data] build];
+}
++ (PBDescriptorProtoExtensionRange*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBDescriptorProtoExtensionRange*)[[[PBDescriptorProtoExtensionRange builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBDescriptorProtoExtensionRange*) parseFromInputStream:(NSInputStream*) input {
+  return (PBDescriptorProtoExtensionRange*)[[[PBDescriptorProtoExtensionRange builder] mergeFromInputStream:input] build];
+}
++ (PBDescriptorProtoExtensionRange*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBDescriptorProtoExtensionRange*)[[[PBDescriptorProtoExtensionRange builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBDescriptorProtoExtensionRange*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBDescriptorProtoExtensionRange*)[[[PBDescriptorProtoExtensionRange builder] mergeFromCodedInputStream:input] build];
+}
++ (PBDescriptorProtoExtensionRange*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBDescriptorProtoExtensionRange*)[[[PBDescriptorProtoExtensionRange builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBDescriptorProtoExtensionRangeBuilder*) builder {
+  return [[PBDescriptorProtoExtensionRangeBuilder alloc] init];
+}
++ (PBDescriptorProtoExtensionRangeBuilder*) builderWithPrototype:(PBDescriptorProtoExtensionRange*) prototype {
+  return [[PBDescriptorProtoExtensionRange builder] mergeFrom:prototype];
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) builder {
+  return [PBDescriptorProtoExtensionRange builder];
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) toBuilder {
+  return [PBDescriptorProtoExtensionRange builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasStart) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"start", [NSNumber numberWithInteger:self.start]];
+  }
+  if (self.hasEnd) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"end", [NSNumber numberWithInteger:self.end]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBDescriptorProtoExtensionRange class]]) {
+    return NO;
+  }
+  PBDescriptorProtoExtensionRange *otherMessage = other;
+  return
+      self.hasStart == otherMessage.hasStart &&
+      (!self.hasStart || self.start == otherMessage.start) &&
+      self.hasEnd == otherMessage.hasEnd &&
+      (!self.hasEnd || self.end == otherMessage.end) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasStart) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.start] hash];
+  }
+  if (self.hasEnd) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.end] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBDescriptorProtoExtensionRangeBuilder()
+@property (strong) PBDescriptorProtoExtensionRange* result;
+@end
+
+@implementation PBDescriptorProtoExtensionRangeBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBDescriptorProtoExtensionRange alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) clear {
+  self.result = [[PBDescriptorProtoExtensionRange alloc] init];
+  return self;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) clone {
+  return [PBDescriptorProtoExtensionRange builderWithPrototype:result];
+}
+- (PBDescriptorProtoExtensionRange*) defaultInstance {
+  return [PBDescriptorProtoExtensionRange defaultInstance];
+}
+- (PBDescriptorProtoExtensionRange*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBDescriptorProtoExtensionRange*) buildPartial {
+  PBDescriptorProtoExtensionRange* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) mergeFrom:(PBDescriptorProtoExtensionRange*) other {
+  if (other == [PBDescriptorProtoExtensionRange defaultInstance]) {
+    return self;
+  }
+  if (other.hasStart) {
+    [self setStart:other.start];
+  }
+  if (other.hasEnd) {
+    [self setEnd:other.end];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setStart:[input readInt32]];
+        break;
+      }
+      case 16: {
+        [self setEnd:[input readInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasStart {
+  return result.hasStart;
+}
+- (SInt32) start {
+  return result.start;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) setStart:(SInt32) value {
+  result.hasStart = YES;
+  result.start = value;
+  return self;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) clearStart {
+  result.hasStart = NO;
+  result.start = 0;
+  return self;
+}
+- (BOOL) hasEnd {
+  return result.hasEnd;
+}
+- (SInt32) end {
+  return result.end;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) setEnd:(SInt32) value {
+  result.hasEnd = YES;
+  result.end = value;
+  return self;
+}
+- (PBDescriptorProtoExtensionRangeBuilder*) clearEnd {
+  result.hasEnd = NO;
+  result.end = 0;
+  return self;
+}
+@end
+
+@interface PBDescriptorProtoBuilder()
+@property (strong) PBDescriptorProto* result;
+@end
+
+@implementation PBDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBDescriptorProtoBuilder*) clear {
+  self.result = [[PBDescriptorProto alloc] init];
+  return self;
+}
+- (PBDescriptorProtoBuilder*) clone {
+  return [PBDescriptorProto builderWithPrototype:result];
+}
+- (PBDescriptorProto*) defaultInstance {
+  return [PBDescriptorProto defaultInstance];
+}
+- (PBDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBDescriptorProto*) buildPartial {
+  PBDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBDescriptorProtoBuilder*) mergeFrom:(PBDescriptorProto*) other {
+  if (other == [PBDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  if (other.fieldArray.count > 0) {
+    if (result.fieldArray == nil) {
+      result.fieldArray = [[NSMutableArray alloc] initWithArray:other.fieldArray];
+    } else {
+      [result.fieldArray addObjectsFromArray:other.fieldArray];
+    }
+  }
+  if (other.extensionArray.count > 0) {
+    if (result.extensionArray == nil) {
+      result.extensionArray = [[NSMutableArray alloc] initWithArray:other.extensionArray];
+    } else {
+      [result.extensionArray addObjectsFromArray:other.extensionArray];
+    }
+  }
+  if (other.nestedTypeArray.count > 0) {
+    if (result.nestedTypeArray == nil) {
+      result.nestedTypeArray = [[NSMutableArray alloc] initWithArray:other.nestedTypeArray];
+    } else {
+      [result.nestedTypeArray addObjectsFromArray:other.nestedTypeArray];
+    }
+  }
+  if (other.enumTypeArray.count > 0) {
+    if (result.enumTypeArray == nil) {
+      result.enumTypeArray = [[NSMutableArray alloc] initWithArray:other.enumTypeArray];
+    } else {
+      [result.enumTypeArray addObjectsFromArray:other.enumTypeArray];
+    }
+  }
+  if (other.extensionRangeArray.count > 0) {
+    if (result.extensionRangeArray == nil) {
+      result.extensionRangeArray = [[NSMutableArray alloc] initWithArray:other.extensionRangeArray];
+    } else {
+      [result.extensionRangeArray addObjectsFromArray:other.extensionRangeArray];
+    }
+  }
+  if (other.oneofDeclArray.count > 0) {
+    if (result.oneofDeclArray == nil) {
+      result.oneofDeclArray = [[NSMutableArray alloc] initWithArray:other.oneofDeclArray];
+    } else {
+      [result.oneofDeclArray addObjectsFromArray:other.oneofDeclArray];
+    }
+  }
+  if (other.hasOptions) {
+    [self mergeOptions:other.options];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+      case 18: {
+        PBFieldDescriptorProtoBuilder* subBuilder = [PBFieldDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addField:[subBuilder buildPartial]];
+        break;
+      }
+      case 26: {
+        PBDescriptorProtoBuilder* subBuilder = [PBDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addNestedType:[subBuilder buildPartial]];
+        break;
+      }
+      case 34: {
+        PBEnumDescriptorProtoBuilder* subBuilder = [PBEnumDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addEnumType:[subBuilder buildPartial]];
+        break;
+      }
+      case 42: {
+        PBDescriptorProtoExtensionRangeBuilder* subBuilder = [PBDescriptorProtoExtensionRange builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addExtensionRange:[subBuilder buildPartial]];
+        break;
+      }
+      case 50: {
+        PBFieldDescriptorProtoBuilder* subBuilder = [PBFieldDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addExtension:[subBuilder buildPartial]];
+        break;
+      }
+      case 58: {
+        PBMessageOptionsBuilder* subBuilder = [PBMessageOptions builder];
+        if (self.hasOptions) {
+          [subBuilder mergeFrom:self.options];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setOptions:[subBuilder buildPartial]];
+        break;
+      }
+      case 66: {
+        PBOneofDescriptorProtoBuilder* subBuilder = [PBOneofDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addOneofDecl:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+- (NSMutableArray *)field {
+  return result.fieldArray;
+}
+- (PBFieldDescriptorProto*)fieldAtIndex:(NSUInteger)index {
+  return [result fieldAtIndex:index];
+}
+- (PBDescriptorProtoBuilder *)addField:(PBFieldDescriptorProto*)value {
+  if (result.fieldArray == nil) {
+    result.fieldArray = [[NSMutableArray alloc]init];
+  }
+  [result.fieldArray addObject:value];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)setFieldArray:(NSArray *)array {
+  result.fieldArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)clearField {
+  result.fieldArray = nil;
+  return self;
+}
+- (NSMutableArray *)extension {
+  return result.extensionArray;
+}
+- (PBFieldDescriptorProto*)extensionAtIndex:(NSUInteger)index {
+  return [result extensionAtIndex:index];
+}
+- (PBDescriptorProtoBuilder *)addExtension:(PBFieldDescriptorProto*)value {
+  if (result.extensionArray == nil) {
+    result.extensionArray = [[NSMutableArray alloc]init];
+  }
+  [result.extensionArray addObject:value];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)setExtensionArray:(NSArray *)array {
+  result.extensionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)clearExtension {
+  result.extensionArray = nil;
+  return self;
+}
+- (NSMutableArray *)nestedType {
+  return result.nestedTypeArray;
+}
+- (PBDescriptorProto*)nestedTypeAtIndex:(NSUInteger)index {
+  return [result nestedTypeAtIndex:index];
+}
+- (PBDescriptorProtoBuilder *)addNestedType:(PBDescriptorProto*)value {
+  if (result.nestedTypeArray == nil) {
+    result.nestedTypeArray = [[NSMutableArray alloc]init];
+  }
+  [result.nestedTypeArray addObject:value];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)setNestedTypeArray:(NSArray *)array {
+  result.nestedTypeArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)clearNestedType {
+  result.nestedTypeArray = nil;
+  return self;
+}
+- (NSMutableArray *)enumType {
+  return result.enumTypeArray;
+}
+- (PBEnumDescriptorProto*)enumTypeAtIndex:(NSUInteger)index {
+  return [result enumTypeAtIndex:index];
+}
+- (PBDescriptorProtoBuilder *)addEnumType:(PBEnumDescriptorProto*)value {
+  if (result.enumTypeArray == nil) {
+    result.enumTypeArray = [[NSMutableArray alloc]init];
+  }
+  [result.enumTypeArray addObject:value];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)setEnumTypeArray:(NSArray *)array {
+  result.enumTypeArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)clearEnumType {
+  result.enumTypeArray = nil;
+  return self;
+}
+- (NSMutableArray *)extensionRange {
+  return result.extensionRangeArray;
+}
+- (PBDescriptorProtoExtensionRange*)extensionRangeAtIndex:(NSUInteger)index {
+  return [result extensionRangeAtIndex:index];
+}
+- (PBDescriptorProtoBuilder *)addExtensionRange:(PBDescriptorProtoExtensionRange*)value {
+  if (result.extensionRangeArray == nil) {
+    result.extensionRangeArray = [[NSMutableArray alloc]init];
+  }
+  [result.extensionRangeArray addObject:value];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)setExtensionRangeArray:(NSArray *)array {
+  result.extensionRangeArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)clearExtensionRange {
+  result.extensionRangeArray = nil;
+  return self;
+}
+- (NSMutableArray *)oneofDecl {
+  return result.oneofDeclArray;
+}
+- (PBOneofDescriptorProto*)oneofDeclAtIndex:(NSUInteger)index {
+  return [result oneofDeclAtIndex:index];
+}
+- (PBDescriptorProtoBuilder *)addOneofDecl:(PBOneofDescriptorProto*)value {
+  if (result.oneofDeclArray == nil) {
+    result.oneofDeclArray = [[NSMutableArray alloc]init];
+  }
+  [result.oneofDeclArray addObject:value];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)setOneofDeclArray:(NSArray *)array {
+  result.oneofDeclArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBDescriptorProtoBuilder *)clearOneofDecl {
+  result.oneofDeclArray = nil;
+  return self;
+}
+- (BOOL) hasOptions {
+  return result.hasOptions;
+}
+- (PBMessageOptions*) options {
+  return result.options;
+}
+- (PBDescriptorProtoBuilder*) setOptions:(PBMessageOptions*) value {
+  result.hasOptions = YES;
+  result.options = value;
+  return self;
+}
+- (PBDescriptorProtoBuilder*) setOptionsBuilder:(PBMessageOptionsBuilder*) builderForValue {
+  return [self setOptions:[builderForValue build]];
+}
+- (PBDescriptorProtoBuilder*) mergeOptions:(PBMessageOptions*) value {
+  if (result.hasOptions &&
+      result.options != [PBMessageOptions defaultInstance]) {
+    result.options =
+      [[[PBMessageOptions builderWithPrototype:result.options] mergeFrom:value] buildPartial];
+  } else {
+    result.options = value;
+  }
+  result.hasOptions = YES;
+  return self;
+}
+- (PBDescriptorProtoBuilder*) clearOptions {
+  result.hasOptions = NO;
+  result.options = [PBMessageOptions defaultInstance];
+  return self;
+}
+@end
+
+@interface PBFieldDescriptorProto ()
+@property (strong) NSString* name;
+@property SInt32 number;
+@property PBFieldDescriptorProtoLabel label;
+@property PBFieldDescriptorProtoType type;
+@property (strong) NSString* typeName;
+@property (strong) NSString* extendee;
+@property (strong) NSString* defaultValue;
+@property SInt32 oneofIndex;
+@property (strong) PBFieldOptions* options;
+@end
+
+@implementation PBFieldDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+- (BOOL) hasNumber {
+  return !!hasNumber_;
+}
+- (void) setHasNumber:(BOOL) value_ {
+  hasNumber_ = !!value_;
+}
+@synthesize number;
+- (BOOL) hasLabel {
+  return !!hasLabel_;
+}
+- (void) setHasLabel:(BOOL) value_ {
+  hasLabel_ = !!value_;
+}
+@synthesize label;
+- (BOOL) hasType {
+  return !!hasType_;
+}
+- (void) setHasType:(BOOL) value_ {
+  hasType_ = !!value_;
+}
+@synthesize type;
+- (BOOL) hasTypeName {
+  return !!hasTypeName_;
+}
+- (void) setHasTypeName:(BOOL) value_ {
+  hasTypeName_ = !!value_;
+}
+@synthesize typeName;
+- (BOOL) hasExtendee {
+  return !!hasExtendee_;
+}
+- (void) setHasExtendee:(BOOL) value_ {
+  hasExtendee_ = !!value_;
+}
+@synthesize extendee;
+- (BOOL) hasDefaultValue {
+  return !!hasDefaultValue_;
+}
+- (void) setHasDefaultValue:(BOOL) value_ {
+  hasDefaultValue_ = !!value_;
+}
+@synthesize defaultValue;
+- (BOOL) hasOneofIndex {
+  return !!hasOneofIndex_;
+}
+- (void) setHasOneofIndex:(BOOL) value_ {
+  hasOneofIndex_ = !!value_;
+}
+@synthesize oneofIndex;
+- (BOOL) hasOptions {
+  return !!hasOptions_;
+}
+- (void) setHasOptions:(BOOL) value_ {
+  hasOptions_ = !!value_;
+}
+@synthesize options;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+    self.number = 0;
+    self.label = PBFieldDescriptorProtoLabelLabelOptional;
+    self.type = PBFieldDescriptorProtoTypeTypeDouble;
+    self.typeName = @"";
+    self.extendee = @"";
+    self.defaultValue = @"";
+    self.oneofIndex = 0;
+    self.options = [PBFieldOptions defaultInstance];
+  }
+  return self;
+}
+static PBFieldDescriptorProto* defaultPBFieldDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBFieldDescriptorProto class]) {
+    defaultPBFieldDescriptorProtoInstance = [[PBFieldDescriptorProto alloc] init];
+  }
+}
++ (PBFieldDescriptorProto*) defaultInstance {
+  return defaultPBFieldDescriptorProtoInstance;
+}
+- (PBFieldDescriptorProto*) defaultInstance {
+  return defaultPBFieldDescriptorProtoInstance;
+}
+- (BOOL) isInitialized {
+  if (self.hasOptions) {
+    if (!self.options.isInitialized) {
+      return NO;
+    }
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  if (self.hasExtendee) {
+    [output writeString:2 value:self.extendee];
+  }
+  if (self.hasNumber) {
+    [output writeInt32:3 value:self.number];
+  }
+  if (self.hasLabel) {
+    [output writeEnum:4 value:self.label];
+  }
+  if (self.hasType) {
+    [output writeEnum:5 value:self.type];
+  }
+  if (self.hasTypeName) {
+    [output writeString:6 value:self.typeName];
+  }
+  if (self.hasDefaultValue) {
+    [output writeString:7 value:self.defaultValue];
+  }
+  if (self.hasOptions) {
+    [output writeMessage:8 value:self.options];
+  }
+  if (self.hasOneofIndex) {
+    [output writeInt32:9 value:self.oneofIndex];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  if (self.hasExtendee) {
+    size_ += computeStringSize(2, self.extendee);
+  }
+  if (self.hasNumber) {
+    size_ += computeInt32Size(3, self.number);
+  }
+  if (self.hasLabel) {
+    size_ += computeEnumSize(4, self.label);
+  }
+  if (self.hasType) {
+    size_ += computeEnumSize(5, self.type);
+  }
+  if (self.hasTypeName) {
+    size_ += computeStringSize(6, self.typeName);
+  }
+  if (self.hasDefaultValue) {
+    size_ += computeStringSize(7, self.defaultValue);
+  }
+  if (self.hasOptions) {
+    size_ += computeMessageSize(8, self.options);
+  }
+  if (self.hasOneofIndex) {
+    size_ += computeInt32Size(9, self.oneofIndex);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBFieldDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBFieldDescriptorProto*)[[[PBFieldDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBFieldDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFieldDescriptorProto*)[[[PBFieldDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBFieldDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBFieldDescriptorProto*)[[[PBFieldDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBFieldDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFieldDescriptorProto*)[[[PBFieldDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFieldDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBFieldDescriptorProto*)[[[PBFieldDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBFieldDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFieldDescriptorProto*)[[[PBFieldDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFieldDescriptorProtoBuilder*) builder {
+  return [[PBFieldDescriptorProtoBuilder alloc] init];
+}
++ (PBFieldDescriptorProtoBuilder*) builderWithPrototype:(PBFieldDescriptorProto*) prototype {
+  return [[PBFieldDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBFieldDescriptorProtoBuilder*) builder {
+  return [PBFieldDescriptorProto builder];
+}
+- (PBFieldDescriptorProtoBuilder*) toBuilder {
+  return [PBFieldDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  if (self.hasExtendee) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"extendee", self.extendee];
+  }
+  if (self.hasNumber) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"number", [NSNumber numberWithInteger:self.number]];
+  }
+  if (self.hasLabel) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"label", self.label];
+  }
+  if (self.hasType) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"type", self.type];
+  }
+  if (self.hasTypeName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"typeName", self.typeName];
+  }
+  if (self.hasDefaultValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"defaultValue", self.defaultValue];
+  }
+  if (self.hasOptions) {
+    [output appendFormat:@"%@%@ {\n", indent, @"options"];
+    [self.options writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  if (self.hasOneofIndex) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"oneofIndex", [NSNumber numberWithInteger:self.oneofIndex]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBFieldDescriptorProto class]]) {
+    return NO;
+  }
+  PBFieldDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      self.hasExtendee == otherMessage.hasExtendee &&
+      (!self.hasExtendee || [self.extendee isEqual:otherMessage.extendee]) &&
+      self.hasNumber == otherMessage.hasNumber &&
+      (!self.hasNumber || self.number == otherMessage.number) &&
+      self.hasLabel == otherMessage.hasLabel &&
+      (!self.hasLabel || self.label == otherMessage.label) &&
+      self.hasType == otherMessage.hasType &&
+      (!self.hasType || self.type == otherMessage.type) &&
+      self.hasTypeName == otherMessage.hasTypeName &&
+      (!self.hasTypeName || [self.typeName isEqual:otherMessage.typeName]) &&
+      self.hasDefaultValue == otherMessage.hasDefaultValue &&
+      (!self.hasDefaultValue || [self.defaultValue isEqual:otherMessage.defaultValue]) &&
+      self.hasOptions == otherMessage.hasOptions &&
+      (!self.hasOptions || [self.options isEqual:otherMessage.options]) &&
+      self.hasOneofIndex == otherMessage.hasOneofIndex &&
+      (!self.hasOneofIndex || self.oneofIndex == otherMessage.oneofIndex) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  if (self.hasExtendee) {
+    hashCode = hashCode * 31 + [self.extendee hash];
+  }
+  if (self.hasNumber) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.number] hash];
+  }
+  if (self.hasLabel) {
+    hashCode = hashCode * 31 + self.label;
+  }
+  if (self.hasType) {
+    hashCode = hashCode * 31 + self.type;
+  }
+  if (self.hasTypeName) {
+    hashCode = hashCode * 31 + [self.typeName hash];
+  }
+  if (self.hasDefaultValue) {
+    hashCode = hashCode * 31 + [self.defaultValue hash];
+  }
+  if (self.hasOptions) {
+    hashCode = hashCode * 31 + [self.options hash];
+  }
+  if (self.hasOneofIndex) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.oneofIndex] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL PBFieldDescriptorProtoTypeIsValidValue(PBFieldDescriptorProtoType value) {
+  switch (value) {
+    case PBFieldDescriptorProtoTypeTypeDouble:
+    case PBFieldDescriptorProtoTypeTypeFloat:
+    case PBFieldDescriptorProtoTypeTypeInt64:
+    case PBFieldDescriptorProtoTypeTypeUint64:
+    case PBFieldDescriptorProtoTypeTypeInt32:
+    case PBFieldDescriptorProtoTypeTypeFixed64:
+    case PBFieldDescriptorProtoTypeTypeFixed32:
+    case PBFieldDescriptorProtoTypeTypeBool:
+    case PBFieldDescriptorProtoTypeTypeString:
+    case PBFieldDescriptorProtoTypeTypeGroup:
+    case PBFieldDescriptorProtoTypeTypeMessage:
+    case PBFieldDescriptorProtoTypeTypeBytes:
+    case PBFieldDescriptorProtoTypeTypeUint32:
+    case PBFieldDescriptorProtoTypeTypeEnum:
+    case PBFieldDescriptorProtoTypeTypeSfixed32:
+    case PBFieldDescriptorProtoTypeTypeSfixed64:
+    case PBFieldDescriptorProtoTypeTypeSint32:
+    case PBFieldDescriptorProtoTypeTypeSint64:
+      return YES;
+    default:
+      return NO;
+  }
+}
+BOOL PBFieldDescriptorProtoLabelIsValidValue(PBFieldDescriptorProtoLabel value) {
+  switch (value) {
+    case PBFieldDescriptorProtoLabelLabelOptional:
+    case PBFieldDescriptorProtoLabelLabelRequired:
+    case PBFieldDescriptorProtoLabelLabelRepeated:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface PBFieldDescriptorProtoBuilder()
+@property (strong) PBFieldDescriptorProto* result;
+@end
+
+@implementation PBFieldDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBFieldDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBFieldDescriptorProtoBuilder*) clear {
+  self.result = [[PBFieldDescriptorProto alloc] init];
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clone {
+  return [PBFieldDescriptorProto builderWithPrototype:result];
+}
+- (PBFieldDescriptorProto*) defaultInstance {
+  return [PBFieldDescriptorProto defaultInstance];
+}
+- (PBFieldDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBFieldDescriptorProto*) buildPartial {
+  PBFieldDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBFieldDescriptorProtoBuilder*) mergeFrom:(PBFieldDescriptorProto*) other {
+  if (other == [PBFieldDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  if (other.hasNumber) {
+    [self setNumber:other.number];
+  }
+  if (other.hasLabel) {
+    [self setLabel:other.label];
+  }
+  if (other.hasType) {
+    [self setType:other.type];
+  }
+  if (other.hasTypeName) {
+    [self setTypeName:other.typeName];
+  }
+  if (other.hasExtendee) {
+    [self setExtendee:other.extendee];
+  }
+  if (other.hasDefaultValue) {
+    [self setDefaultValue:other.defaultValue];
+  }
+  if (other.hasOneofIndex) {
+    [self setOneofIndex:other.oneofIndex];
+  }
+  if (other.hasOptions) {
+    [self mergeOptions:other.options];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBFieldDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+      case 18: {
+        [self setExtendee:[input readString]];
+        break;
+      }
+      case 24: {
+        [self setNumber:[input readInt32]];
+        break;
+      }
+      case 32: {
+        PBFieldDescriptorProtoLabel value = (PBFieldDescriptorProtoLabel)[input readEnum];
+        if (PBFieldDescriptorProtoLabelIsValidValue(value)) {
+          [self setLabel:value];
+        } else {
+          [unknownFields mergeVarintField:4 value:value];
+        }
+        break;
+      }
+      case 40: {
+        PBFieldDescriptorProtoType value = (PBFieldDescriptorProtoType)[input readEnum];
+        if (PBFieldDescriptorProtoTypeIsValidValue(value)) {
+          [self setType:value];
+        } else {
+          [unknownFields mergeVarintField:5 value:value];
+        }
+        break;
+      }
+      case 50: {
+        [self setTypeName:[input readString]];
+        break;
+      }
+      case 58: {
+        [self setDefaultValue:[input readString]];
+        break;
+      }
+      case 66: {
+        PBFieldOptionsBuilder* subBuilder = [PBFieldOptions builder];
+        if (self.hasOptions) {
+          [subBuilder mergeFrom:self.options];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setOptions:[subBuilder buildPartial]];
+        break;
+      }
+      case 72: {
+        [self setOneofIndex:[input readInt32]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBFieldDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+- (BOOL) hasNumber {
+  return result.hasNumber;
+}
+- (SInt32) number {
+  return result.number;
+}
+- (PBFieldDescriptorProtoBuilder*) setNumber:(SInt32) value {
+  result.hasNumber = YES;
+  result.number = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearNumber {
+  result.hasNumber = NO;
+  result.number = 0;
+  return self;
+}
+- (BOOL) hasLabel {
+  return result.hasLabel;
+}
+- (PBFieldDescriptorProtoLabel) label {
+  return result.label;
+}
+- (PBFieldDescriptorProtoBuilder*) setLabel:(PBFieldDescriptorProtoLabel) value {
+  result.hasLabel = YES;
+  result.label = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearLabel {
+  result.hasLabel = NO;
+  result.label = PBFieldDescriptorProtoLabelLabelOptional;
+  return self;
+}
+- (BOOL) hasType {
+  return result.hasType;
+}
+- (PBFieldDescriptorProtoType) type {
+  return result.type;
+}
+- (PBFieldDescriptorProtoBuilder*) setType:(PBFieldDescriptorProtoType) value {
+  result.hasType = YES;
+  result.type = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearType {
+  result.hasType = NO;
+  result.type = PBFieldDescriptorProtoTypeTypeDouble;
+  return self;
+}
+- (BOOL) hasTypeName {
+  return result.hasTypeName;
+}
+- (NSString*) typeName {
+  return result.typeName;
+}
+- (PBFieldDescriptorProtoBuilder*) setTypeName:(NSString*) value {
+  result.hasTypeName = YES;
+  result.typeName = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearTypeName {
+  result.hasTypeName = NO;
+  result.typeName = @"";
+  return self;
+}
+- (BOOL) hasExtendee {
+  return result.hasExtendee;
+}
+- (NSString*) extendee {
+  return result.extendee;
+}
+- (PBFieldDescriptorProtoBuilder*) setExtendee:(NSString*) value {
+  result.hasExtendee = YES;
+  result.extendee = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearExtendee {
+  result.hasExtendee = NO;
+  result.extendee = @"";
+  return self;
+}
+- (BOOL) hasDefaultValue {
+  return result.hasDefaultValue;
+}
+- (NSString*) defaultValue {
+  return result.defaultValue;
+}
+- (PBFieldDescriptorProtoBuilder*) setDefaultValue:(NSString*) value {
+  result.hasDefaultValue = YES;
+  result.defaultValue = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearDefaultValue {
+  result.hasDefaultValue = NO;
+  result.defaultValue = @"";
+  return self;
+}
+- (BOOL) hasOneofIndex {
+  return result.hasOneofIndex;
+}
+- (SInt32) oneofIndex {
+  return result.oneofIndex;
+}
+- (PBFieldDescriptorProtoBuilder*) setOneofIndex:(SInt32) value {
+  result.hasOneofIndex = YES;
+  result.oneofIndex = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearOneofIndex {
+  result.hasOneofIndex = NO;
+  result.oneofIndex = 0;
+  return self;
+}
+- (BOOL) hasOptions {
+  return result.hasOptions;
+}
+- (PBFieldOptions*) options {
+  return result.options;
+}
+- (PBFieldDescriptorProtoBuilder*) setOptions:(PBFieldOptions*) value {
+  result.hasOptions = YES;
+  result.options = value;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) setOptionsBuilder:(PBFieldOptionsBuilder*) builderForValue {
+  return [self setOptions:[builderForValue build]];
+}
+- (PBFieldDescriptorProtoBuilder*) mergeOptions:(PBFieldOptions*) value {
+  if (result.hasOptions &&
+      result.options != [PBFieldOptions defaultInstance]) {
+    result.options =
+      [[[PBFieldOptions builderWithPrototype:result.options] mergeFrom:value] buildPartial];
+  } else {
+    result.options = value;
+  }
+  result.hasOptions = YES;
+  return self;
+}
+- (PBFieldDescriptorProtoBuilder*) clearOptions {
+  result.hasOptions = NO;
+  result.options = [PBFieldOptions defaultInstance];
+  return self;
+}
+@end
+
+@interface PBOneofDescriptorProto ()
+@property (strong) NSString* name;
+@end
+
+@implementation PBOneofDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+  }
+  return self;
+}
+static PBOneofDescriptorProto* defaultPBOneofDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBOneofDescriptorProto class]) {
+    defaultPBOneofDescriptorProtoInstance = [[PBOneofDescriptorProto alloc] init];
+  }
+}
++ (PBOneofDescriptorProto*) defaultInstance {
+  return defaultPBOneofDescriptorProtoInstance;
+}
+- (PBOneofDescriptorProto*) defaultInstance {
+  return defaultPBOneofDescriptorProtoInstance;
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBOneofDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBOneofDescriptorProto*)[[[PBOneofDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBOneofDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBOneofDescriptorProto*)[[[PBOneofDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBOneofDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBOneofDescriptorProto*)[[[PBOneofDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBOneofDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBOneofDescriptorProto*)[[[PBOneofDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBOneofDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBOneofDescriptorProto*)[[[PBOneofDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBOneofDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBOneofDescriptorProto*)[[[PBOneofDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBOneofDescriptorProtoBuilder*) builder {
+  return [[PBOneofDescriptorProtoBuilder alloc] init];
+}
++ (PBOneofDescriptorProtoBuilder*) builderWithPrototype:(PBOneofDescriptorProto*) prototype {
+  return [[PBOneofDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBOneofDescriptorProtoBuilder*) builder {
+  return [PBOneofDescriptorProto builder];
+}
+- (PBOneofDescriptorProtoBuilder*) toBuilder {
+  return [PBOneofDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBOneofDescriptorProto class]]) {
+    return NO;
+  }
+  PBOneofDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBOneofDescriptorProtoBuilder()
+@property (strong) PBOneofDescriptorProto* result;
+@end
+
+@implementation PBOneofDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBOneofDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBOneofDescriptorProtoBuilder*) clear {
+  self.result = [[PBOneofDescriptorProto alloc] init];
+  return self;
+}
+- (PBOneofDescriptorProtoBuilder*) clone {
+  return [PBOneofDescriptorProto builderWithPrototype:result];
+}
+- (PBOneofDescriptorProto*) defaultInstance {
+  return [PBOneofDescriptorProto defaultInstance];
+}
+- (PBOneofDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBOneofDescriptorProto*) buildPartial {
+  PBOneofDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBOneofDescriptorProtoBuilder*) mergeFrom:(PBOneofDescriptorProto*) other {
+  if (other == [PBOneofDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBOneofDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBOneofDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBOneofDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBOneofDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+@end
+
+@interface PBEnumDescriptorProto ()
+@property (strong) NSString* name;
+@property (strong) NSMutableArray * valueArray;
+@property (strong) PBEnumOptions* options;
+@end
+
+@implementation PBEnumDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+@synthesize valueArray;
+@dynamic value;
+- (BOOL) hasOptions {
+  return !!hasOptions_;
+}
+- (void) setHasOptions:(BOOL) value_ {
+  hasOptions_ = !!value_;
+}
+@synthesize options;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+    self.options = [PBEnumOptions defaultInstance];
+  }
+  return self;
+}
+static PBEnumDescriptorProto* defaultPBEnumDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBEnumDescriptorProto class]) {
+    defaultPBEnumDescriptorProtoInstance = [[PBEnumDescriptorProto alloc] init];
+  }
+}
++ (PBEnumDescriptorProto*) defaultInstance {
+  return defaultPBEnumDescriptorProtoInstance;
+}
+- (PBEnumDescriptorProto*) defaultInstance {
+  return defaultPBEnumDescriptorProtoInstance;
+}
+- (NSArray *)value {
+  return valueArray;
+}
+- (PBEnumValueDescriptorProto*)valueAtIndex:(NSUInteger)index {
+  return [valueArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInitvalue = YES;
+   [self.value enumerateObjectsUsingBlock:^(PBEnumValueDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitvalue = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitvalue) return isInitvalue;
+  if (self.hasOptions) {
+    if (!self.options.isInitialized) {
+      return NO;
+    }
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  [self.valueArray enumerateObjectsUsingBlock:^(PBEnumValueDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:2 value:element];
+  }];
+  if (self.hasOptions) {
+    [output writeMessage:3 value:self.options];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  [self.valueArray enumerateObjectsUsingBlock:^(PBEnumValueDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(2, element);
+  }];
+  if (self.hasOptions) {
+    size_ += computeMessageSize(3, self.options);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBEnumDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBEnumDescriptorProto*)[[[PBEnumDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBEnumDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumDescriptorProto*)[[[PBEnumDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBEnumDescriptorProto*)[[[PBEnumDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBEnumDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumDescriptorProto*)[[[PBEnumDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBEnumDescriptorProto*)[[[PBEnumDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBEnumDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumDescriptorProto*)[[[PBEnumDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumDescriptorProtoBuilder*) builder {
+  return [[PBEnumDescriptorProtoBuilder alloc] init];
+}
++ (PBEnumDescriptorProtoBuilder*) builderWithPrototype:(PBEnumDescriptorProto*) prototype {
+  return [[PBEnumDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBEnumDescriptorProtoBuilder*) builder {
+  return [PBEnumDescriptorProto builder];
+}
+- (PBEnumDescriptorProtoBuilder*) toBuilder {
+  return [PBEnumDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  [self.valueArray enumerateObjectsUsingBlock:^(PBEnumValueDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"value"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasOptions) {
+    [output appendFormat:@"%@%@ {\n", indent, @"options"];
+    [self.options writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBEnumDescriptorProto class]]) {
+    return NO;
+  }
+  PBEnumDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      [self.valueArray isEqualToArray:otherMessage.valueArray] &&
+      self.hasOptions == otherMessage.hasOptions &&
+      (!self.hasOptions || [self.options isEqual:otherMessage.options]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  [self.valueArray enumerateObjectsUsingBlock:^(PBEnumValueDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasOptions) {
+    hashCode = hashCode * 31 + [self.options hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBEnumDescriptorProtoBuilder()
+@property (strong) PBEnumDescriptorProto* result;
+@end
+
+@implementation PBEnumDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBEnumDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBEnumDescriptorProtoBuilder*) clear {
+  self.result = [[PBEnumDescriptorProto alloc] init];
+  return self;
+}
+- (PBEnumDescriptorProtoBuilder*) clone {
+  return [PBEnumDescriptorProto builderWithPrototype:result];
+}
+- (PBEnumDescriptorProto*) defaultInstance {
+  return [PBEnumDescriptorProto defaultInstance];
+}
+- (PBEnumDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBEnumDescriptorProto*) buildPartial {
+  PBEnumDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBEnumDescriptorProtoBuilder*) mergeFrom:(PBEnumDescriptorProto*) other {
+  if (other == [PBEnumDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  if (other.valueArray.count > 0) {
+    if (result.valueArray == nil) {
+      result.valueArray = [[NSMutableArray alloc] initWithArray:other.valueArray];
+    } else {
+      [result.valueArray addObjectsFromArray:other.valueArray];
+    }
+  }
+  if (other.hasOptions) {
+    [self mergeOptions:other.options];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBEnumDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBEnumDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+      case 18: {
+        PBEnumValueDescriptorProtoBuilder* subBuilder = [PBEnumValueDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addValue:[subBuilder buildPartial]];
+        break;
+      }
+      case 26: {
+        PBEnumOptionsBuilder* subBuilder = [PBEnumOptions builder];
+        if (self.hasOptions) {
+          [subBuilder mergeFrom:self.options];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setOptions:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBEnumDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBEnumDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+- (NSMutableArray *)value {
+  return result.valueArray;
+}
+- (PBEnumValueDescriptorProto*)valueAtIndex:(NSUInteger)index {
+  return [result valueAtIndex:index];
+}
+- (PBEnumDescriptorProtoBuilder *)addValue:(PBEnumValueDescriptorProto*)value {
+  if (result.valueArray == nil) {
+    result.valueArray = [[NSMutableArray alloc]init];
+  }
+  [result.valueArray addObject:value];
+  return self;
+}
+- (PBEnumDescriptorProtoBuilder *)setValueArray:(NSArray *)array {
+  result.valueArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBEnumDescriptorProtoBuilder *)clearValue {
+  result.valueArray = nil;
+  return self;
+}
+- (BOOL) hasOptions {
+  return result.hasOptions;
+}
+- (PBEnumOptions*) options {
+  return result.options;
+}
+- (PBEnumDescriptorProtoBuilder*) setOptions:(PBEnumOptions*) value {
+  result.hasOptions = YES;
+  result.options = value;
+  return self;
+}
+- (PBEnumDescriptorProtoBuilder*) setOptionsBuilder:(PBEnumOptionsBuilder*) builderForValue {
+  return [self setOptions:[builderForValue build]];
+}
+- (PBEnumDescriptorProtoBuilder*) mergeOptions:(PBEnumOptions*) value {
+  if (result.hasOptions &&
+      result.options != [PBEnumOptions defaultInstance]) {
+    result.options =
+      [[[PBEnumOptions builderWithPrototype:result.options] mergeFrom:value] buildPartial];
+  } else {
+    result.options = value;
+  }
+  result.hasOptions = YES;
+  return self;
+}
+- (PBEnumDescriptorProtoBuilder*) clearOptions {
+  result.hasOptions = NO;
+  result.options = [PBEnumOptions defaultInstance];
+  return self;
+}
+@end
+
+@interface PBEnumValueDescriptorProto ()
+@property (strong) NSString* name;
+@property SInt32 number;
+@property (strong) PBEnumValueOptions* options;
+@end
+
+@implementation PBEnumValueDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+- (BOOL) hasNumber {
+  return !!hasNumber_;
+}
+- (void) setHasNumber:(BOOL) value_ {
+  hasNumber_ = !!value_;
+}
+@synthesize number;
+- (BOOL) hasOptions {
+  return !!hasOptions_;
+}
+- (void) setHasOptions:(BOOL) value_ {
+  hasOptions_ = !!value_;
+}
+@synthesize options;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+    self.number = 0;
+    self.options = [PBEnumValueOptions defaultInstance];
+  }
+  return self;
+}
+static PBEnumValueDescriptorProto* defaultPBEnumValueDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBEnumValueDescriptorProto class]) {
+    defaultPBEnumValueDescriptorProtoInstance = [[PBEnumValueDescriptorProto alloc] init];
+  }
+}
++ (PBEnumValueDescriptorProto*) defaultInstance {
+  return defaultPBEnumValueDescriptorProtoInstance;
+}
+- (PBEnumValueDescriptorProto*) defaultInstance {
+  return defaultPBEnumValueDescriptorProtoInstance;
+}
+- (BOOL) isInitialized {
+  if (self.hasOptions) {
+    if (!self.options.isInitialized) {
+      return NO;
+    }
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  if (self.hasNumber) {
+    [output writeInt32:2 value:self.number];
+  }
+  if (self.hasOptions) {
+    [output writeMessage:3 value:self.options];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  if (self.hasNumber) {
+    size_ += computeInt32Size(2, self.number);
+  }
+  if (self.hasOptions) {
+    size_ += computeMessageSize(3, self.options);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBEnumValueDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBEnumValueDescriptorProto*)[[[PBEnumValueDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBEnumValueDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumValueDescriptorProto*)[[[PBEnumValueDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumValueDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBEnumValueDescriptorProto*)[[[PBEnumValueDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBEnumValueDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumValueDescriptorProto*)[[[PBEnumValueDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumValueDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBEnumValueDescriptorProto*)[[[PBEnumValueDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBEnumValueDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumValueDescriptorProto*)[[[PBEnumValueDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumValueDescriptorProtoBuilder*) builder {
+  return [[PBEnumValueDescriptorProtoBuilder alloc] init];
+}
++ (PBEnumValueDescriptorProtoBuilder*) builderWithPrototype:(PBEnumValueDescriptorProto*) prototype {
+  return [[PBEnumValueDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBEnumValueDescriptorProtoBuilder*) builder {
+  return [PBEnumValueDescriptorProto builder];
+}
+- (PBEnumValueDescriptorProtoBuilder*) toBuilder {
+  return [PBEnumValueDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  if (self.hasNumber) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"number", [NSNumber numberWithInteger:self.number]];
+  }
+  if (self.hasOptions) {
+    [output appendFormat:@"%@%@ {\n", indent, @"options"];
+    [self.options writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBEnumValueDescriptorProto class]]) {
+    return NO;
+  }
+  PBEnumValueDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      self.hasNumber == otherMessage.hasNumber &&
+      (!self.hasNumber || self.number == otherMessage.number) &&
+      self.hasOptions == otherMessage.hasOptions &&
+      (!self.hasOptions || [self.options isEqual:otherMessage.options]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  if (self.hasNumber) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithInteger:self.number] hash];
+  }
+  if (self.hasOptions) {
+    hashCode = hashCode * 31 + [self.options hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBEnumValueDescriptorProtoBuilder()
+@property (strong) PBEnumValueDescriptorProto* result;
+@end
+
+@implementation PBEnumValueDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBEnumValueDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBEnumValueDescriptorProtoBuilder*) clear {
+  self.result = [[PBEnumValueDescriptorProto alloc] init];
+  return self;
+}
+- (PBEnumValueDescriptorProtoBuilder*) clone {
+  return [PBEnumValueDescriptorProto builderWithPrototype:result];
+}
+- (PBEnumValueDescriptorProto*) defaultInstance {
+  return [PBEnumValueDescriptorProto defaultInstance];
+}
+- (PBEnumValueDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBEnumValueDescriptorProto*) buildPartial {
+  PBEnumValueDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBEnumValueDescriptorProtoBuilder*) mergeFrom:(PBEnumValueDescriptorProto*) other {
+  if (other == [PBEnumValueDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  if (other.hasNumber) {
+    [self setNumber:other.number];
+  }
+  if (other.hasOptions) {
+    [self mergeOptions:other.options];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBEnumValueDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBEnumValueDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+      case 16: {
+        [self setNumber:[input readInt32]];
+        break;
+      }
+      case 26: {
+        PBEnumValueOptionsBuilder* subBuilder = [PBEnumValueOptions builder];
+        if (self.hasOptions) {
+          [subBuilder mergeFrom:self.options];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setOptions:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBEnumValueDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBEnumValueDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+- (BOOL) hasNumber {
+  return result.hasNumber;
+}
+- (SInt32) number {
+  return result.number;
+}
+- (PBEnumValueDescriptorProtoBuilder*) setNumber:(SInt32) value {
+  result.hasNumber = YES;
+  result.number = value;
+  return self;
+}
+- (PBEnumValueDescriptorProtoBuilder*) clearNumber {
+  result.hasNumber = NO;
+  result.number = 0;
+  return self;
+}
+- (BOOL) hasOptions {
+  return result.hasOptions;
+}
+- (PBEnumValueOptions*) options {
+  return result.options;
+}
+- (PBEnumValueDescriptorProtoBuilder*) setOptions:(PBEnumValueOptions*) value {
+  result.hasOptions = YES;
+  result.options = value;
+  return self;
+}
+- (PBEnumValueDescriptorProtoBuilder*) setOptionsBuilder:(PBEnumValueOptionsBuilder*) builderForValue {
+  return [self setOptions:[builderForValue build]];
+}
+- (PBEnumValueDescriptorProtoBuilder*) mergeOptions:(PBEnumValueOptions*) value {
+  if (result.hasOptions &&
+      result.options != [PBEnumValueOptions defaultInstance]) {
+    result.options =
+      [[[PBEnumValueOptions builderWithPrototype:result.options] mergeFrom:value] buildPartial];
+  } else {
+    result.options = value;
+  }
+  result.hasOptions = YES;
+  return self;
+}
+- (PBEnumValueDescriptorProtoBuilder*) clearOptions {
+  result.hasOptions = NO;
+  result.options = [PBEnumValueOptions defaultInstance];
+  return self;
+}
+@end
+
+@interface PBServiceDescriptorProto ()
+@property (strong) NSString* name;
+@property (strong) NSMutableArray * methodArray;
+@property (strong) PBServiceOptions* options;
+@end
+
+@implementation PBServiceDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+@synthesize methodArray;
+@dynamic method;
+- (BOOL) hasOptions {
+  return !!hasOptions_;
+}
+- (void) setHasOptions:(BOOL) value_ {
+  hasOptions_ = !!value_;
+}
+@synthesize options;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+    self.options = [PBServiceOptions defaultInstance];
+  }
+  return self;
+}
+static PBServiceDescriptorProto* defaultPBServiceDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBServiceDescriptorProto class]) {
+    defaultPBServiceDescriptorProtoInstance = [[PBServiceDescriptorProto alloc] init];
+  }
+}
++ (PBServiceDescriptorProto*) defaultInstance {
+  return defaultPBServiceDescriptorProtoInstance;
+}
+- (PBServiceDescriptorProto*) defaultInstance {
+  return defaultPBServiceDescriptorProtoInstance;
+}
+- (NSArray *)method {
+  return methodArray;
+}
+- (PBMethodDescriptorProto*)methodAtIndex:(NSUInteger)index {
+  return [methodArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInitmethod = YES;
+   [self.method enumerateObjectsUsingBlock:^(PBMethodDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitmethod = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitmethod) return isInitmethod;
+  if (self.hasOptions) {
+    if (!self.options.isInitialized) {
+      return NO;
+    }
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  [self.methodArray enumerateObjectsUsingBlock:^(PBMethodDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:2 value:element];
+  }];
+  if (self.hasOptions) {
+    [output writeMessage:3 value:self.options];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  [self.methodArray enumerateObjectsUsingBlock:^(PBMethodDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(2, element);
+  }];
+  if (self.hasOptions) {
+    size_ += computeMessageSize(3, self.options);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBServiceDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBServiceDescriptorProto*)[[[PBServiceDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBServiceDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBServiceDescriptorProto*)[[[PBServiceDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBServiceDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBServiceDescriptorProto*)[[[PBServiceDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBServiceDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBServiceDescriptorProto*)[[[PBServiceDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBServiceDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBServiceDescriptorProto*)[[[PBServiceDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBServiceDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBServiceDescriptorProto*)[[[PBServiceDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBServiceDescriptorProtoBuilder*) builder {
+  return [[PBServiceDescriptorProtoBuilder alloc] init];
+}
++ (PBServiceDescriptorProtoBuilder*) builderWithPrototype:(PBServiceDescriptorProto*) prototype {
+  return [[PBServiceDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBServiceDescriptorProtoBuilder*) builder {
+  return [PBServiceDescriptorProto builder];
+}
+- (PBServiceDescriptorProtoBuilder*) toBuilder {
+  return [PBServiceDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  [self.methodArray enumerateObjectsUsingBlock:^(PBMethodDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"method"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasOptions) {
+    [output appendFormat:@"%@%@ {\n", indent, @"options"];
+    [self.options writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBServiceDescriptorProto class]]) {
+    return NO;
+  }
+  PBServiceDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      [self.methodArray isEqualToArray:otherMessage.methodArray] &&
+      self.hasOptions == otherMessage.hasOptions &&
+      (!self.hasOptions || [self.options isEqual:otherMessage.options]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  [self.methodArray enumerateObjectsUsingBlock:^(PBMethodDescriptorProto *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasOptions) {
+    hashCode = hashCode * 31 + [self.options hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBServiceDescriptorProtoBuilder()
+@property (strong) PBServiceDescriptorProto* result;
+@end
+
+@implementation PBServiceDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBServiceDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBServiceDescriptorProtoBuilder*) clear {
+  self.result = [[PBServiceDescriptorProto alloc] init];
+  return self;
+}
+- (PBServiceDescriptorProtoBuilder*) clone {
+  return [PBServiceDescriptorProto builderWithPrototype:result];
+}
+- (PBServiceDescriptorProto*) defaultInstance {
+  return [PBServiceDescriptorProto defaultInstance];
+}
+- (PBServiceDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBServiceDescriptorProto*) buildPartial {
+  PBServiceDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBServiceDescriptorProtoBuilder*) mergeFrom:(PBServiceDescriptorProto*) other {
+  if (other == [PBServiceDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  if (other.methodArray.count > 0) {
+    if (result.methodArray == nil) {
+      result.methodArray = [[NSMutableArray alloc] initWithArray:other.methodArray];
+    } else {
+      [result.methodArray addObjectsFromArray:other.methodArray];
+    }
+  }
+  if (other.hasOptions) {
+    [self mergeOptions:other.options];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBServiceDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBServiceDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+      case 18: {
+        PBMethodDescriptorProtoBuilder* subBuilder = [PBMethodDescriptorProto builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addMethod:[subBuilder buildPartial]];
+        break;
+      }
+      case 26: {
+        PBServiceOptionsBuilder* subBuilder = [PBServiceOptions builder];
+        if (self.hasOptions) {
+          [subBuilder mergeFrom:self.options];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setOptions:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBServiceDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBServiceDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+- (NSMutableArray *)method {
+  return result.methodArray;
+}
+- (PBMethodDescriptorProto*)methodAtIndex:(NSUInteger)index {
+  return [result methodAtIndex:index];
+}
+- (PBServiceDescriptorProtoBuilder *)addMethod:(PBMethodDescriptorProto*)value {
+  if (result.methodArray == nil) {
+    result.methodArray = [[NSMutableArray alloc]init];
+  }
+  [result.methodArray addObject:value];
+  return self;
+}
+- (PBServiceDescriptorProtoBuilder *)setMethodArray:(NSArray *)array {
+  result.methodArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBServiceDescriptorProtoBuilder *)clearMethod {
+  result.methodArray = nil;
+  return self;
+}
+- (BOOL) hasOptions {
+  return result.hasOptions;
+}
+- (PBServiceOptions*) options {
+  return result.options;
+}
+- (PBServiceDescriptorProtoBuilder*) setOptions:(PBServiceOptions*) value {
+  result.hasOptions = YES;
+  result.options = value;
+  return self;
+}
+- (PBServiceDescriptorProtoBuilder*) setOptionsBuilder:(PBServiceOptionsBuilder*) builderForValue {
+  return [self setOptions:[builderForValue build]];
+}
+- (PBServiceDescriptorProtoBuilder*) mergeOptions:(PBServiceOptions*) value {
+  if (result.hasOptions &&
+      result.options != [PBServiceOptions defaultInstance]) {
+    result.options =
+      [[[PBServiceOptions builderWithPrototype:result.options] mergeFrom:value] buildPartial];
+  } else {
+    result.options = value;
+  }
+  result.hasOptions = YES;
+  return self;
+}
+- (PBServiceDescriptorProtoBuilder*) clearOptions {
+  result.hasOptions = NO;
+  result.options = [PBServiceOptions defaultInstance];
+  return self;
+}
+@end
+
+@interface PBMethodDescriptorProto ()
+@property (strong) NSString* name;
+@property (strong) NSString* inputType;
+@property (strong) NSString* outputType;
+@property (strong) PBMethodOptions* options;
+@end
+
+@implementation PBMethodDescriptorProto
+
+- (BOOL) hasName {
+  return !!hasName_;
+}
+- (void) setHasName:(BOOL) value_ {
+  hasName_ = !!value_;
+}
+@synthesize name;
+- (BOOL) hasInputType {
+  return !!hasInputType_;
+}
+- (void) setHasInputType:(BOOL) value_ {
+  hasInputType_ = !!value_;
+}
+@synthesize inputType;
+- (BOOL) hasOutputType {
+  return !!hasOutputType_;
+}
+- (void) setHasOutputType:(BOOL) value_ {
+  hasOutputType_ = !!value_;
+}
+@synthesize outputType;
+- (BOOL) hasOptions {
+  return !!hasOptions_;
+}
+- (void) setHasOptions:(BOOL) value_ {
+  hasOptions_ = !!value_;
+}
+@synthesize options;
+- (id) init {
+  if ((self = [super init])) {
+    self.name = @"";
+    self.inputType = @"";
+    self.outputType = @"";
+    self.options = [PBMethodOptions defaultInstance];
+  }
+  return self;
+}
+static PBMethodDescriptorProto* defaultPBMethodDescriptorProtoInstance = nil;
++ (void) initialize {
+  if (self == [PBMethodDescriptorProto class]) {
+    defaultPBMethodDescriptorProtoInstance = [[PBMethodDescriptorProto alloc] init];
+  }
+}
++ (PBMethodDescriptorProto*) defaultInstance {
+  return defaultPBMethodDescriptorProtoInstance;
+}
+- (PBMethodDescriptorProto*) defaultInstance {
+  return defaultPBMethodDescriptorProtoInstance;
+}
+- (BOOL) isInitialized {
+  if (self.hasOptions) {
+    if (!self.options.isInitialized) {
+      return NO;
+    }
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasName) {
+    [output writeString:1 value:self.name];
+  }
+  if (self.hasInputType) {
+    [output writeString:2 value:self.inputType];
+  }
+  if (self.hasOutputType) {
+    [output writeString:3 value:self.outputType];
+  }
+  if (self.hasOptions) {
+    [output writeMessage:4 value:self.options];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasName) {
+    size_ += computeStringSize(1, self.name);
+  }
+  if (self.hasInputType) {
+    size_ += computeStringSize(2, self.inputType);
+  }
+  if (self.hasOutputType) {
+    size_ += computeStringSize(3, self.outputType);
+  }
+  if (self.hasOptions) {
+    size_ += computeMessageSize(4, self.options);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBMethodDescriptorProto*) parseFromData:(NSData*) data {
+  return (PBMethodDescriptorProto*)[[[PBMethodDescriptorProto builder] mergeFromData:data] build];
+}
++ (PBMethodDescriptorProto*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMethodDescriptorProto*)[[[PBMethodDescriptorProto builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBMethodDescriptorProto*) parseFromInputStream:(NSInputStream*) input {
+  return (PBMethodDescriptorProto*)[[[PBMethodDescriptorProto builder] mergeFromInputStream:input] build];
+}
++ (PBMethodDescriptorProto*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMethodDescriptorProto*)[[[PBMethodDescriptorProto builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBMethodDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBMethodDescriptorProto*)[[[PBMethodDescriptorProto builder] mergeFromCodedInputStream:input] build];
+}
++ (PBMethodDescriptorProto*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMethodDescriptorProto*)[[[PBMethodDescriptorProto builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBMethodDescriptorProtoBuilder*) builder {
+  return [[PBMethodDescriptorProtoBuilder alloc] init];
+}
++ (PBMethodDescriptorProtoBuilder*) builderWithPrototype:(PBMethodDescriptorProto*) prototype {
+  return [[PBMethodDescriptorProto builder] mergeFrom:prototype];
+}
+- (PBMethodDescriptorProtoBuilder*) builder {
+  return [PBMethodDescriptorProto builder];
+}
+- (PBMethodDescriptorProtoBuilder*) toBuilder {
+  return [PBMethodDescriptorProto builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasName) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"name", self.name];
+  }
+  if (self.hasInputType) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"inputType", self.inputType];
+  }
+  if (self.hasOutputType) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"outputType", self.outputType];
+  }
+  if (self.hasOptions) {
+    [output appendFormat:@"%@%@ {\n", indent, @"options"];
+    [self.options writeDescriptionTo:output
+                         withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBMethodDescriptorProto class]]) {
+    return NO;
+  }
+  PBMethodDescriptorProto *otherMessage = other;
+  return
+      self.hasName == otherMessage.hasName &&
+      (!self.hasName || [self.name isEqual:otherMessage.name]) &&
+      self.hasInputType == otherMessage.hasInputType &&
+      (!self.hasInputType || [self.inputType isEqual:otherMessage.inputType]) &&
+      self.hasOutputType == otherMessage.hasOutputType &&
+      (!self.hasOutputType || [self.outputType isEqual:otherMessage.outputType]) &&
+      self.hasOptions == otherMessage.hasOptions &&
+      (!self.hasOptions || [self.options isEqual:otherMessage.options]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasName) {
+    hashCode = hashCode * 31 + [self.name hash];
+  }
+  if (self.hasInputType) {
+    hashCode = hashCode * 31 + [self.inputType hash];
+  }
+  if (self.hasOutputType) {
+    hashCode = hashCode * 31 + [self.outputType hash];
+  }
+  if (self.hasOptions) {
+    hashCode = hashCode * 31 + [self.options hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBMethodDescriptorProtoBuilder()
+@property (strong) PBMethodDescriptorProto* result;
+@end
+
+@implementation PBMethodDescriptorProtoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBMethodDescriptorProto alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBMethodDescriptorProtoBuilder*) clear {
+  self.result = [[PBMethodDescriptorProto alloc] init];
+  return self;
+}
+- (PBMethodDescriptorProtoBuilder*) clone {
+  return [PBMethodDescriptorProto builderWithPrototype:result];
+}
+- (PBMethodDescriptorProto*) defaultInstance {
+  return [PBMethodDescriptorProto defaultInstance];
+}
+- (PBMethodDescriptorProto*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBMethodDescriptorProto*) buildPartial {
+  PBMethodDescriptorProto* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBMethodDescriptorProtoBuilder*) mergeFrom:(PBMethodDescriptorProto*) other {
+  if (other == [PBMethodDescriptorProto defaultInstance]) {
+    return self;
+  }
+  if (other.hasName) {
+    [self setName:other.name];
+  }
+  if (other.hasInputType) {
+    [self setInputType:other.inputType];
+  }
+  if (other.hasOutputType) {
+    [self setOutputType:other.outputType];
+  }
+  if (other.hasOptions) {
+    [self mergeOptions:other.options];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBMethodDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBMethodDescriptorProtoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setName:[input readString]];
+        break;
+      }
+      case 18: {
+        [self setInputType:[input readString]];
+        break;
+      }
+      case 26: {
+        [self setOutputType:[input readString]];
+        break;
+      }
+      case 34: {
+        PBMethodOptionsBuilder* subBuilder = [PBMethodOptions builder];
+        if (self.hasOptions) {
+          [subBuilder mergeFrom:self.options];
+        }
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self setOptions:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasName {
+  return result.hasName;
+}
+- (NSString*) name {
+  return result.name;
+}
+- (PBMethodDescriptorProtoBuilder*) setName:(NSString*) value {
+  result.hasName = YES;
+  result.name = value;
+  return self;
+}
+- (PBMethodDescriptorProtoBuilder*) clearName {
+  result.hasName = NO;
+  result.name = @"";
+  return self;
+}
+- (BOOL) hasInputType {
+  return result.hasInputType;
+}
+- (NSString*) inputType {
+  return result.inputType;
+}
+- (PBMethodDescriptorProtoBuilder*) setInputType:(NSString*) value {
+  result.hasInputType = YES;
+  result.inputType = value;
+  return self;
+}
+- (PBMethodDescriptorProtoBuilder*) clearInputType {
+  result.hasInputType = NO;
+  result.inputType = @"";
+  return self;
+}
+- (BOOL) hasOutputType {
+  return result.hasOutputType;
+}
+- (NSString*) outputType {
+  return result.outputType;
+}
+- (PBMethodDescriptorProtoBuilder*) setOutputType:(NSString*) value {
+  result.hasOutputType = YES;
+  result.outputType = value;
+  return self;
+}
+- (PBMethodDescriptorProtoBuilder*) clearOutputType {
+  result.hasOutputType = NO;
+  result.outputType = @"";
+  return self;
+}
+- (BOOL) hasOptions {
+  return result.hasOptions;
+}
+- (PBMethodOptions*) options {
+  return result.options;
+}
+- (PBMethodDescriptorProtoBuilder*) setOptions:(PBMethodOptions*) value {
+  result.hasOptions = YES;
+  result.options = value;
+  return self;
+}
+- (PBMethodDescriptorProtoBuilder*) setOptionsBuilder:(PBMethodOptionsBuilder*) builderForValue {
+  return [self setOptions:[builderForValue build]];
+}
+- (PBMethodDescriptorProtoBuilder*) mergeOptions:(PBMethodOptions*) value {
+  if (result.hasOptions &&
+      result.options != [PBMethodOptions defaultInstance]) {
+    result.options =
+      [[[PBMethodOptions builderWithPrototype:result.options] mergeFrom:value] buildPartial];
+  } else {
+    result.options = value;
+  }
+  result.hasOptions = YES;
+  return self;
+}
+- (PBMethodDescriptorProtoBuilder*) clearOptions {
+  result.hasOptions = NO;
+  result.options = [PBMethodOptions defaultInstance];
+  return self;
+}
+@end
+
+@interface PBFileOptions ()
+@property (strong) NSString* javaPackage;
+@property (strong) NSString* javaOuterClassname;
+@property BOOL javaMultipleFiles;
+@property BOOL javaGenerateEqualsAndHash;
+@property BOOL javaStringCheckUtf8;
+@property PBFileOptionsOptimizeMode optimizeFor;
+@property (strong) NSString* goPackage;
+@property BOOL ccGenericServices;
+@property BOOL javaGenericServices;
+@property BOOL pyGenericServices;
+@property BOOL deprecated;
+@property (strong) NSMutableArray * uninterpretedOptionArray;
+@end
+
+@implementation PBFileOptions
+
+- (BOOL) hasJavaPackage {
+  return !!hasJavaPackage_;
+}
+- (void) setHasJavaPackage:(BOOL) value_ {
+  hasJavaPackage_ = !!value_;
+}
+@synthesize javaPackage;
+- (BOOL) hasJavaOuterClassname {
+  return !!hasJavaOuterClassname_;
+}
+- (void) setHasJavaOuterClassname:(BOOL) value_ {
+  hasJavaOuterClassname_ = !!value_;
+}
+@synthesize javaOuterClassname;
+- (BOOL) hasJavaMultipleFiles {
+  return !!hasJavaMultipleFiles_;
+}
+- (void) setHasJavaMultipleFiles:(BOOL) value_ {
+  hasJavaMultipleFiles_ = !!value_;
+}
+- (BOOL) javaMultipleFiles {
+  return !!javaMultipleFiles_;
+}
+- (void) setJavaMultipleFiles:(BOOL) value_ {
+  javaMultipleFiles_ = !!value_;
+}
+- (BOOL) hasJavaGenerateEqualsAndHash {
+  return !!hasJavaGenerateEqualsAndHash_;
+}
+- (void) setHasJavaGenerateEqualsAndHash:(BOOL) value_ {
+  hasJavaGenerateEqualsAndHash_ = !!value_;
+}
+- (BOOL) javaGenerateEqualsAndHash {
+  return !!javaGenerateEqualsAndHash_;
+}
+- (void) setJavaGenerateEqualsAndHash:(BOOL) value_ {
+  javaGenerateEqualsAndHash_ = !!value_;
+}
+- (BOOL) hasJavaStringCheckUtf8 {
+  return !!hasJavaStringCheckUtf8_;
+}
+- (void) setHasJavaStringCheckUtf8:(BOOL) value_ {
+  hasJavaStringCheckUtf8_ = !!value_;
+}
+- (BOOL) javaStringCheckUtf8 {
+  return !!javaStringCheckUtf8_;
+}
+- (void) setJavaStringCheckUtf8:(BOOL) value_ {
+  javaStringCheckUtf8_ = !!value_;
+}
+- (BOOL) hasOptimizeFor {
+  return !!hasOptimizeFor_;
+}
+- (void) setHasOptimizeFor:(BOOL) value_ {
+  hasOptimizeFor_ = !!value_;
+}
+@synthesize optimizeFor;
+- (BOOL) hasGoPackage {
+  return !!hasGoPackage_;
+}
+- (void) setHasGoPackage:(BOOL) value_ {
+  hasGoPackage_ = !!value_;
+}
+@synthesize goPackage;
+- (BOOL) hasCcGenericServices {
+  return !!hasCcGenericServices_;
+}
+- (void) setHasCcGenericServices:(BOOL) value_ {
+  hasCcGenericServices_ = !!value_;
+}
+- (BOOL) ccGenericServices {
+  return !!ccGenericServices_;
+}
+- (void) setCcGenericServices:(BOOL) value_ {
+  ccGenericServices_ = !!value_;
+}
+- (BOOL) hasJavaGenericServices {
+  return !!hasJavaGenericServices_;
+}
+- (void) setHasJavaGenericServices:(BOOL) value_ {
+  hasJavaGenericServices_ = !!value_;
+}
+- (BOOL) javaGenericServices {
+  return !!javaGenericServices_;
+}
+- (void) setJavaGenericServices:(BOOL) value_ {
+  javaGenericServices_ = !!value_;
+}
+- (BOOL) hasPyGenericServices {
+  return !!hasPyGenericServices_;
+}
+- (void) setHasPyGenericServices:(BOOL) value_ {
+  hasPyGenericServices_ = !!value_;
+}
+- (BOOL) pyGenericServices {
+  return !!pyGenericServices_;
+}
+- (void) setPyGenericServices:(BOOL) value_ {
+  pyGenericServices_ = !!value_;
+}
+- (BOOL) hasDeprecated {
+  return !!hasDeprecated_;
+}
+- (void) setHasDeprecated:(BOOL) value_ {
+  hasDeprecated_ = !!value_;
+}
+- (BOOL) deprecated {
+  return !!deprecated_;
+}
+- (void) setDeprecated:(BOOL) value_ {
+  deprecated_ = !!value_;
+}
+@synthesize uninterpretedOptionArray;
+@dynamic uninterpretedOption;
+- (id) init {
+  if ((self = [super init])) {
+    self.javaPackage = @"";
+    self.javaOuterClassname = @"";
+    self.javaMultipleFiles = NO;
+    self.javaGenerateEqualsAndHash = NO;
+    self.javaStringCheckUtf8 = NO;
+    self.optimizeFor = PBFileOptionsOptimizeModeSpeed;
+    self.goPackage = @"";
+    self.ccGenericServices = NO;
+    self.javaGenericServices = NO;
+    self.pyGenericServices = NO;
+    self.deprecated = NO;
+  }
+  return self;
+}
+static PBFileOptions* defaultPBFileOptionsInstance = nil;
++ (void) initialize {
+  if (self == [PBFileOptions class]) {
+    defaultPBFileOptionsInstance = [[PBFileOptions alloc] init];
+  }
+}
++ (PBFileOptions*) defaultInstance {
+  return defaultPBFileOptionsInstance;
+}
+- (PBFileOptions*) defaultInstance {
+  return defaultPBFileOptionsInstance;
+}
+- (NSArray *)uninterpretedOption {
+  return uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [uninterpretedOptionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInituninterpretedOption = YES;
+   [self.uninterpretedOption enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInituninterpretedOption = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInituninterpretedOption) return isInituninterpretedOption;
+  if (!self.extensionsAreInitialized) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasJavaPackage) {
+    [output writeString:1 value:self.javaPackage];
+  }
+  if (self.hasJavaOuterClassname) {
+    [output writeString:8 value:self.javaOuterClassname];
+  }
+  if (self.hasOptimizeFor) {
+    [output writeEnum:9 value:self.optimizeFor];
+  }
+  if (self.hasJavaMultipleFiles) {
+    [output writeBool:10 value:self.javaMultipleFiles];
+  }
+  if (self.hasGoPackage) {
+    [output writeString:11 value:self.goPackage];
+  }
+  if (self.hasCcGenericServices) {
+    [output writeBool:16 value:self.ccGenericServices];
+  }
+  if (self.hasJavaGenericServices) {
+    [output writeBool:17 value:self.javaGenericServices];
+  }
+  if (self.hasPyGenericServices) {
+    [output writeBool:18 value:self.pyGenericServices];
+  }
+  if (self.hasJavaGenerateEqualsAndHash) {
+    [output writeBool:20 value:self.javaGenerateEqualsAndHash];
+  }
+  if (self.hasDeprecated) {
+    [output writeBool:23 value:self.deprecated];
+  }
+  if (self.hasJavaStringCheckUtf8) {
+    [output writeBool:27 value:self.javaStringCheckUtf8];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:999 value:element];
+  }];
+  [self writeExtensionsToCodedOutputStream:output
+                                      from:1000
+                                        to:536870912];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasJavaPackage) {
+    size_ += computeStringSize(1, self.javaPackage);
+  }
+  if (self.hasJavaOuterClassname) {
+    size_ += computeStringSize(8, self.javaOuterClassname);
+  }
+  if (self.hasOptimizeFor) {
+    size_ += computeEnumSize(9, self.optimizeFor);
+  }
+  if (self.hasJavaMultipleFiles) {
+    size_ += computeBoolSize(10, self.javaMultipleFiles);
+  }
+  if (self.hasGoPackage) {
+    size_ += computeStringSize(11, self.goPackage);
+  }
+  if (self.hasCcGenericServices) {
+    size_ += computeBoolSize(16, self.ccGenericServices);
+  }
+  if (self.hasJavaGenericServices) {
+    size_ += computeBoolSize(17, self.javaGenericServices);
+  }
+  if (self.hasPyGenericServices) {
+    size_ += computeBoolSize(18, self.pyGenericServices);
+  }
+  if (self.hasJavaGenerateEqualsAndHash) {
+    size_ += computeBoolSize(20, self.javaGenerateEqualsAndHash);
+  }
+  if (self.hasDeprecated) {
+    size_ += computeBoolSize(23, self.deprecated);
+  }
+  if (self.hasJavaStringCheckUtf8) {
+    size_ += computeBoolSize(27, self.javaStringCheckUtf8);
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(999, element);
+  }];
+  size_ += [self extensionsSerializedSize];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBFileOptions*) parseFromData:(NSData*) data {
+  return (PBFileOptions*)[[[PBFileOptions builder] mergeFromData:data] build];
+}
++ (PBFileOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileOptions*)[[[PBFileOptions builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBFileOptions*) parseFromInputStream:(NSInputStream*) input {
+  return (PBFileOptions*)[[[PBFileOptions builder] mergeFromInputStream:input] build];
+}
++ (PBFileOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileOptions*)[[[PBFileOptions builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFileOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBFileOptions*)[[[PBFileOptions builder] mergeFromCodedInputStream:input] build];
+}
++ (PBFileOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFileOptions*)[[[PBFileOptions builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFileOptionsBuilder*) builder {
+  return [[PBFileOptionsBuilder alloc] init];
+}
++ (PBFileOptionsBuilder*) builderWithPrototype:(PBFileOptions*) prototype {
+  return [[PBFileOptions builder] mergeFrom:prototype];
+}
+- (PBFileOptionsBuilder*) builder {
+  return [PBFileOptions builder];
+}
+- (PBFileOptionsBuilder*) toBuilder {
+  return [PBFileOptions builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasJavaPackage) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"javaPackage", self.javaPackage];
+  }
+  if (self.hasJavaOuterClassname) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"javaOuterClassname", self.javaOuterClassname];
+  }
+  if (self.hasOptimizeFor) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"optimizeFor", self.optimizeFor];
+  }
+  if (self.hasJavaMultipleFiles) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"javaMultipleFiles", [NSNumber numberWithBool:self.javaMultipleFiles]];
+  }
+  if (self.hasGoPackage) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"goPackage", self.goPackage];
+  }
+  if (self.hasCcGenericServices) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"ccGenericServices", [NSNumber numberWithBool:self.ccGenericServices]];
+  }
+  if (self.hasJavaGenericServices) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"javaGenericServices", [NSNumber numberWithBool:self.javaGenericServices]];
+  }
+  if (self.hasPyGenericServices) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"pyGenericServices", [NSNumber numberWithBool:self.pyGenericServices]];
+  }
+  if (self.hasJavaGenerateEqualsAndHash) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"javaGenerateEqualsAndHash", [NSNumber numberWithBool:self.javaGenerateEqualsAndHash]];
+  }
+  if (self.hasDeprecated) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deprecated", [NSNumber numberWithBool:self.deprecated]];
+  }
+  if (self.hasJavaStringCheckUtf8) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"javaStringCheckUtf8", [NSNumber numberWithBool:self.javaStringCheckUtf8]];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"uninterpretedOption"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self writeExtensionDescriptionToMutableString:(NSMutableString*)output
+                                            from:1000
+                                              to:536870912
+                                      withIndent:indent];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBFileOptions class]]) {
+    return NO;
+  }
+  PBFileOptions *otherMessage = other;
+  return
+      self.hasJavaPackage == otherMessage.hasJavaPackage &&
+      (!self.hasJavaPackage || [self.javaPackage isEqual:otherMessage.javaPackage]) &&
+      self.hasJavaOuterClassname == otherMessage.hasJavaOuterClassname &&
+      (!self.hasJavaOuterClassname || [self.javaOuterClassname isEqual:otherMessage.javaOuterClassname]) &&
+      self.hasOptimizeFor == otherMessage.hasOptimizeFor &&
+      (!self.hasOptimizeFor || self.optimizeFor == otherMessage.optimizeFor) &&
+      self.hasJavaMultipleFiles == otherMessage.hasJavaMultipleFiles &&
+      (!self.hasJavaMultipleFiles || self.javaMultipleFiles == otherMessage.javaMultipleFiles) &&
+      self.hasGoPackage == otherMessage.hasGoPackage &&
+      (!self.hasGoPackage || [self.goPackage isEqual:otherMessage.goPackage]) &&
+      self.hasCcGenericServices == otherMessage.hasCcGenericServices &&
+      (!self.hasCcGenericServices || self.ccGenericServices == otherMessage.ccGenericServices) &&
+      self.hasJavaGenericServices == otherMessage.hasJavaGenericServices &&
+      (!self.hasJavaGenericServices || self.javaGenericServices == otherMessage.javaGenericServices) &&
+      self.hasPyGenericServices == otherMessage.hasPyGenericServices &&
+      (!self.hasPyGenericServices || self.pyGenericServices == otherMessage.pyGenericServices) &&
+      self.hasJavaGenerateEqualsAndHash == otherMessage.hasJavaGenerateEqualsAndHash &&
+      (!self.hasJavaGenerateEqualsAndHash || self.javaGenerateEqualsAndHash == otherMessage.javaGenerateEqualsAndHash) &&
+      self.hasDeprecated == otherMessage.hasDeprecated &&
+      (!self.hasDeprecated || self.deprecated == otherMessage.deprecated) &&
+      self.hasJavaStringCheckUtf8 == otherMessage.hasJavaStringCheckUtf8 &&
+      (!self.hasJavaStringCheckUtf8 || self.javaStringCheckUtf8 == otherMessage.javaStringCheckUtf8) &&
+      [self.uninterpretedOptionArray isEqualToArray:otherMessage.uninterpretedOptionArray] &&
+      [self isEqualExtensionsInOther:otherMessage from:1000 to:536870912] &&
+
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasJavaPackage) {
+    hashCode = hashCode * 31 + [self.javaPackage hash];
+  }
+  if (self.hasJavaOuterClassname) {
+    hashCode = hashCode * 31 + [self.javaOuterClassname hash];
+  }
+  if (self.hasOptimizeFor) {
+    hashCode = hashCode * 31 + self.optimizeFor;
+  }
+  if (self.hasJavaMultipleFiles) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.javaMultipleFiles] hash];
+  }
+  if (self.hasGoPackage) {
+    hashCode = hashCode * 31 + [self.goPackage hash];
+  }
+  if (self.hasCcGenericServices) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.ccGenericServices] hash];
+  }
+  if (self.hasJavaGenericServices) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.javaGenericServices] hash];
+  }
+  if (self.hasPyGenericServices) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.pyGenericServices] hash];
+  }
+  if (self.hasJavaGenerateEqualsAndHash) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.javaGenerateEqualsAndHash] hash];
+  }
+  if (self.hasDeprecated) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.deprecated] hash];
+  }
+  if (self.hasJavaStringCheckUtf8) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.javaStringCheckUtf8] hash];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self hashExtensionsFrom:1000 to:536870912];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL PBFileOptionsOptimizeModeIsValidValue(PBFileOptionsOptimizeMode value) {
+  switch (value) {
+    case PBFileOptionsOptimizeModeSpeed:
+    case PBFileOptionsOptimizeModeCodeSize:
+    case PBFileOptionsOptimizeModeLiteRuntime:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface PBFileOptionsBuilder()
+@property (strong) PBFileOptions* result;
+@end
+
+@implementation PBFileOptionsBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBFileOptions alloc] init];
+  }
+  return self;
+}
+- (PBExtendableMessage*) internalGetResult {
+  return result;
+}
+- (PBFileOptionsBuilder*) clear {
+  self.result = [[PBFileOptions alloc] init];
+  return self;
+}
+- (PBFileOptionsBuilder*) clone {
+  return [PBFileOptions builderWithPrototype:result];
+}
+- (PBFileOptions*) defaultInstance {
+  return [PBFileOptions defaultInstance];
+}
+- (PBFileOptions*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBFileOptions*) buildPartial {
+  PBFileOptions* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBFileOptionsBuilder*) mergeFrom:(PBFileOptions*) other {
+  if (other == [PBFileOptions defaultInstance]) {
+    return self;
+  }
+  if (other.hasJavaPackage) {
+    [self setJavaPackage:other.javaPackage];
+  }
+  if (other.hasJavaOuterClassname) {
+    [self setJavaOuterClassname:other.javaOuterClassname];
+  }
+  if (other.hasJavaMultipleFiles) {
+    [self setJavaMultipleFiles:other.javaMultipleFiles];
+  }
+  if (other.hasJavaGenerateEqualsAndHash) {
+    [self setJavaGenerateEqualsAndHash:other.javaGenerateEqualsAndHash];
+  }
+  if (other.hasJavaStringCheckUtf8) {
+    [self setJavaStringCheckUtf8:other.javaStringCheckUtf8];
+  }
+  if (other.hasOptimizeFor) {
+    [self setOptimizeFor:other.optimizeFor];
+  }
+  if (other.hasGoPackage) {
+    [self setGoPackage:other.goPackage];
+  }
+  if (other.hasCcGenericServices) {
+    [self setCcGenericServices:other.ccGenericServices];
+  }
+  if (other.hasJavaGenericServices) {
+    [self setJavaGenericServices:other.javaGenericServices];
+  }
+  if (other.hasPyGenericServices) {
+    [self setPyGenericServices:other.pyGenericServices];
+  }
+  if (other.hasDeprecated) {
+    [self setDeprecated:other.deprecated];
+  }
+  if (other.uninterpretedOptionArray.count > 0) {
+    if (result.uninterpretedOptionArray == nil) {
+      result.uninterpretedOptionArray = [[NSMutableArray alloc] initWithArray:other.uninterpretedOptionArray];
+    } else {
+      [result.uninterpretedOptionArray addObjectsFromArray:other.uninterpretedOptionArray];
+    }
+  }
+  [self mergeExtensionFields:other];
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBFileOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBFileOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setJavaPackage:[input readString]];
+        break;
+      }
+      case 66: {
+        [self setJavaOuterClassname:[input readString]];
+        break;
+      }
+      case 72: {
+        PBFileOptionsOptimizeMode value = (PBFileOptionsOptimizeMode)[input readEnum];
+        if (PBFileOptionsOptimizeModeIsValidValue(value)) {
+          [self setOptimizeFor:value];
+        } else {
+          [unknownFields mergeVarintField:9 value:value];
+        }
+        break;
+      }
+      case 80: {
+        [self setJavaMultipleFiles:[input readBool]];
+        break;
+      }
+      case 90: {
+        [self setGoPackage:[input readString]];
+        break;
+      }
+      case 128: {
+        [self setCcGenericServices:[input readBool]];
+        break;
+      }
+      case 136: {
+        [self setJavaGenericServices:[input readBool]];
+        break;
+      }
+      case 144: {
+        [self setPyGenericServices:[input readBool]];
+        break;
+      }
+      case 160: {
+        [self setJavaGenerateEqualsAndHash:[input readBool]];
+        break;
+      }
+      case 184: {
+        [self setDeprecated:[input readBool]];
+        break;
+      }
+      case 216: {
+        [self setJavaStringCheckUtf8:[input readBool]];
+        break;
+      }
+      case 7994: {
+        PBUninterpretedOptionBuilder* subBuilder = [PBUninterpretedOption builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addUninterpretedOption:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasJavaPackage {
+  return result.hasJavaPackage;
+}
+- (NSString*) javaPackage {
+  return result.javaPackage;
+}
+- (PBFileOptionsBuilder*) setJavaPackage:(NSString*) value {
+  result.hasJavaPackage = YES;
+  result.javaPackage = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearJavaPackage {
+  result.hasJavaPackage = NO;
+  result.javaPackage = @"";
+  return self;
+}
+- (BOOL) hasJavaOuterClassname {
+  return result.hasJavaOuterClassname;
+}
+- (NSString*) javaOuterClassname {
+  return result.javaOuterClassname;
+}
+- (PBFileOptionsBuilder*) setJavaOuterClassname:(NSString*) value {
+  result.hasJavaOuterClassname = YES;
+  result.javaOuterClassname = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearJavaOuterClassname {
+  result.hasJavaOuterClassname = NO;
+  result.javaOuterClassname = @"";
+  return self;
+}
+- (BOOL) hasJavaMultipleFiles {
+  return result.hasJavaMultipleFiles;
+}
+- (BOOL) javaMultipleFiles {
+  return result.javaMultipleFiles;
+}
+- (PBFileOptionsBuilder*) setJavaMultipleFiles:(BOOL) value {
+  result.hasJavaMultipleFiles = YES;
+  result.javaMultipleFiles = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearJavaMultipleFiles {
+  result.hasJavaMultipleFiles = NO;
+  result.javaMultipleFiles = NO;
+  return self;
+}
+- (BOOL) hasJavaGenerateEqualsAndHash {
+  return result.hasJavaGenerateEqualsAndHash;
+}
+- (BOOL) javaGenerateEqualsAndHash {
+  return result.javaGenerateEqualsAndHash;
+}
+- (PBFileOptionsBuilder*) setJavaGenerateEqualsAndHash:(BOOL) value {
+  result.hasJavaGenerateEqualsAndHash = YES;
+  result.javaGenerateEqualsAndHash = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearJavaGenerateEqualsAndHash {
+  result.hasJavaGenerateEqualsAndHash = NO;
+  result.javaGenerateEqualsAndHash = NO;
+  return self;
+}
+- (BOOL) hasJavaStringCheckUtf8 {
+  return result.hasJavaStringCheckUtf8;
+}
+- (BOOL) javaStringCheckUtf8 {
+  return result.javaStringCheckUtf8;
+}
+- (PBFileOptionsBuilder*) setJavaStringCheckUtf8:(BOOL) value {
+  result.hasJavaStringCheckUtf8 = YES;
+  result.javaStringCheckUtf8 = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearJavaStringCheckUtf8 {
+  result.hasJavaStringCheckUtf8 = NO;
+  result.javaStringCheckUtf8 = NO;
+  return self;
+}
+- (BOOL) hasOptimizeFor {
+  return result.hasOptimizeFor;
+}
+- (PBFileOptionsOptimizeMode) optimizeFor {
+  return result.optimizeFor;
+}
+- (PBFileOptionsBuilder*) setOptimizeFor:(PBFileOptionsOptimizeMode) value {
+  result.hasOptimizeFor = YES;
+  result.optimizeFor = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearOptimizeFor {
+  result.hasOptimizeFor = NO;
+  result.optimizeFor = PBFileOptionsOptimizeModeSpeed;
+  return self;
+}
+- (BOOL) hasGoPackage {
+  return result.hasGoPackage;
+}
+- (NSString*) goPackage {
+  return result.goPackage;
+}
+- (PBFileOptionsBuilder*) setGoPackage:(NSString*) value {
+  result.hasGoPackage = YES;
+  result.goPackage = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearGoPackage {
+  result.hasGoPackage = NO;
+  result.goPackage = @"";
+  return self;
+}
+- (BOOL) hasCcGenericServices {
+  return result.hasCcGenericServices;
+}
+- (BOOL) ccGenericServices {
+  return result.ccGenericServices;
+}
+- (PBFileOptionsBuilder*) setCcGenericServices:(BOOL) value {
+  result.hasCcGenericServices = YES;
+  result.ccGenericServices = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearCcGenericServices {
+  result.hasCcGenericServices = NO;
+  result.ccGenericServices = NO;
+  return self;
+}
+- (BOOL) hasJavaGenericServices {
+  return result.hasJavaGenericServices;
+}
+- (BOOL) javaGenericServices {
+  return result.javaGenericServices;
+}
+- (PBFileOptionsBuilder*) setJavaGenericServices:(BOOL) value {
+  result.hasJavaGenericServices = YES;
+  result.javaGenericServices = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearJavaGenericServices {
+  result.hasJavaGenericServices = NO;
+  result.javaGenericServices = NO;
+  return self;
+}
+- (BOOL) hasPyGenericServices {
+  return result.hasPyGenericServices;
+}
+- (BOOL) pyGenericServices {
+  return result.pyGenericServices;
+}
+- (PBFileOptionsBuilder*) setPyGenericServices:(BOOL) value {
+  result.hasPyGenericServices = YES;
+  result.pyGenericServices = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearPyGenericServices {
+  result.hasPyGenericServices = NO;
+  result.pyGenericServices = NO;
+  return self;
+}
+- (BOOL) hasDeprecated {
+  return result.hasDeprecated;
+}
+- (BOOL) deprecated {
+  return result.deprecated;
+}
+- (PBFileOptionsBuilder*) setDeprecated:(BOOL) value {
+  result.hasDeprecated = YES;
+  result.deprecated = value;
+  return self;
+}
+- (PBFileOptionsBuilder*) clearDeprecated {
+  result.hasDeprecated = NO;
+  result.deprecated = NO;
+  return self;
+}
+- (NSMutableArray *)uninterpretedOption {
+  return result.uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [result uninterpretedOptionAtIndex:index];
+}
+- (PBFileOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value {
+  if (result.uninterpretedOptionArray == nil) {
+    result.uninterpretedOptionArray = [[NSMutableArray alloc]init];
+  }
+  [result.uninterpretedOptionArray addObject:value];
+  return self;
+}
+- (PBFileOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array {
+  result.uninterpretedOptionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBFileOptionsBuilder *)clearUninterpretedOption {
+  result.uninterpretedOptionArray = nil;
+  return self;
+}
+@end
+
+@interface PBMessageOptions ()
+@property BOOL messageSetWireFormat;
+@property BOOL noStandardDescriptorAccessor;
+@property BOOL deprecated;
+@property (strong) NSMutableArray * uninterpretedOptionArray;
+@end
+
+@implementation PBMessageOptions
+
+- (BOOL) hasMessageSetWireFormat {
+  return !!hasMessageSetWireFormat_;
+}
+- (void) setHasMessageSetWireFormat:(BOOL) value_ {
+  hasMessageSetWireFormat_ = !!value_;
+}
+- (BOOL) messageSetWireFormat {
+  return !!messageSetWireFormat_;
+}
+- (void) setMessageSetWireFormat:(BOOL) value_ {
+  messageSetWireFormat_ = !!value_;
+}
+- (BOOL) hasNoStandardDescriptorAccessor {
+  return !!hasNoStandardDescriptorAccessor_;
+}
+- (void) setHasNoStandardDescriptorAccessor:(BOOL) value_ {
+  hasNoStandardDescriptorAccessor_ = !!value_;
+}
+- (BOOL) noStandardDescriptorAccessor {
+  return !!noStandardDescriptorAccessor_;
+}
+- (void) setNoStandardDescriptorAccessor:(BOOL) value_ {
+  noStandardDescriptorAccessor_ = !!value_;
+}
+- (BOOL) hasDeprecated {
+  return !!hasDeprecated_;
+}
+- (void) setHasDeprecated:(BOOL) value_ {
+  hasDeprecated_ = !!value_;
+}
+- (BOOL) deprecated {
+  return !!deprecated_;
+}
+- (void) setDeprecated:(BOOL) value_ {
+  deprecated_ = !!value_;
+}
+@synthesize uninterpretedOptionArray;
+@dynamic uninterpretedOption;
+- (id) init {
+  if ((self = [super init])) {
+    self.messageSetWireFormat = NO;
+    self.noStandardDescriptorAccessor = NO;
+    self.deprecated = NO;
+  }
+  return self;
+}
+static PBMessageOptions* defaultPBMessageOptionsInstance = nil;
++ (void) initialize {
+  if (self == [PBMessageOptions class]) {
+    defaultPBMessageOptionsInstance = [[PBMessageOptions alloc] init];
+  }
+}
++ (PBMessageOptions*) defaultInstance {
+  return defaultPBMessageOptionsInstance;
+}
+- (PBMessageOptions*) defaultInstance {
+  return defaultPBMessageOptionsInstance;
+}
+- (NSArray *)uninterpretedOption {
+  return uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [uninterpretedOptionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInituninterpretedOption = YES;
+   [self.uninterpretedOption enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInituninterpretedOption = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInituninterpretedOption) return isInituninterpretedOption;
+  if (!self.extensionsAreInitialized) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasMessageSetWireFormat) {
+    [output writeBool:1 value:self.messageSetWireFormat];
+  }
+  if (self.hasNoStandardDescriptorAccessor) {
+    [output writeBool:2 value:self.noStandardDescriptorAccessor];
+  }
+  if (self.hasDeprecated) {
+    [output writeBool:3 value:self.deprecated];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:999 value:element];
+  }];
+  [self writeExtensionsToCodedOutputStream:output
+                                      from:1000
+                                        to:536870912];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasMessageSetWireFormat) {
+    size_ += computeBoolSize(1, self.messageSetWireFormat);
+  }
+  if (self.hasNoStandardDescriptorAccessor) {
+    size_ += computeBoolSize(2, self.noStandardDescriptorAccessor);
+  }
+  if (self.hasDeprecated) {
+    size_ += computeBoolSize(3, self.deprecated);
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(999, element);
+  }];
+  size_ += [self extensionsSerializedSize];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBMessageOptions*) parseFromData:(NSData*) data {
+  return (PBMessageOptions*)[[[PBMessageOptions builder] mergeFromData:data] build];
+}
++ (PBMessageOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMessageOptions*)[[[PBMessageOptions builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBMessageOptions*) parseFromInputStream:(NSInputStream*) input {
+  return (PBMessageOptions*)[[[PBMessageOptions builder] mergeFromInputStream:input] build];
+}
++ (PBMessageOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMessageOptions*)[[[PBMessageOptions builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBMessageOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBMessageOptions*)[[[PBMessageOptions builder] mergeFromCodedInputStream:input] build];
+}
++ (PBMessageOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMessageOptions*)[[[PBMessageOptions builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBMessageOptionsBuilder*) builder {
+  return [[PBMessageOptionsBuilder alloc] init];
+}
++ (PBMessageOptionsBuilder*) builderWithPrototype:(PBMessageOptions*) prototype {
+  return [[PBMessageOptions builder] mergeFrom:prototype];
+}
+- (PBMessageOptionsBuilder*) builder {
+  return [PBMessageOptions builder];
+}
+- (PBMessageOptionsBuilder*) toBuilder {
+  return [PBMessageOptions builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasMessageSetWireFormat) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"messageSetWireFormat", [NSNumber numberWithBool:self.messageSetWireFormat]];
+  }
+  if (self.hasNoStandardDescriptorAccessor) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"noStandardDescriptorAccessor", [NSNumber numberWithBool:self.noStandardDescriptorAccessor]];
+  }
+  if (self.hasDeprecated) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deprecated", [NSNumber numberWithBool:self.deprecated]];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"uninterpretedOption"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self writeExtensionDescriptionToMutableString:(NSMutableString*)output
+                                            from:1000
+                                              to:536870912
+                                      withIndent:indent];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBMessageOptions class]]) {
+    return NO;
+  }
+  PBMessageOptions *otherMessage = other;
+  return
+      self.hasMessageSetWireFormat == otherMessage.hasMessageSetWireFormat &&
+      (!self.hasMessageSetWireFormat || self.messageSetWireFormat == otherMessage.messageSetWireFormat) &&
+      self.hasNoStandardDescriptorAccessor == otherMessage.hasNoStandardDescriptorAccessor &&
+      (!self.hasNoStandardDescriptorAccessor || self.noStandardDescriptorAccessor == otherMessage.noStandardDescriptorAccessor) &&
+      self.hasDeprecated == otherMessage.hasDeprecated &&
+      (!self.hasDeprecated || self.deprecated == otherMessage.deprecated) &&
+      [self.uninterpretedOptionArray isEqualToArray:otherMessage.uninterpretedOptionArray] &&
+      [self isEqualExtensionsInOther:otherMessage from:1000 to:536870912] &&
+
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasMessageSetWireFormat) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.messageSetWireFormat] hash];
+  }
+  if (self.hasNoStandardDescriptorAccessor) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.noStandardDescriptorAccessor] hash];
+  }
+  if (self.hasDeprecated) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.deprecated] hash];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self hashExtensionsFrom:1000 to:536870912];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBMessageOptionsBuilder()
+@property (strong) PBMessageOptions* result;
+@end
+
+@implementation PBMessageOptionsBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBMessageOptions alloc] init];
+  }
+  return self;
+}
+- (PBExtendableMessage*) internalGetResult {
+  return result;
+}
+- (PBMessageOptionsBuilder*) clear {
+  self.result = [[PBMessageOptions alloc] init];
+  return self;
+}
+- (PBMessageOptionsBuilder*) clone {
+  return [PBMessageOptions builderWithPrototype:result];
+}
+- (PBMessageOptions*) defaultInstance {
+  return [PBMessageOptions defaultInstance];
+}
+- (PBMessageOptions*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBMessageOptions*) buildPartial {
+  PBMessageOptions* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBMessageOptionsBuilder*) mergeFrom:(PBMessageOptions*) other {
+  if (other == [PBMessageOptions defaultInstance]) {
+    return self;
+  }
+  if (other.hasMessageSetWireFormat) {
+    [self setMessageSetWireFormat:other.messageSetWireFormat];
+  }
+  if (other.hasNoStandardDescriptorAccessor) {
+    [self setNoStandardDescriptorAccessor:other.noStandardDescriptorAccessor];
+  }
+  if (other.hasDeprecated) {
+    [self setDeprecated:other.deprecated];
+  }
+  if (other.uninterpretedOptionArray.count > 0) {
+    if (result.uninterpretedOptionArray == nil) {
+      result.uninterpretedOptionArray = [[NSMutableArray alloc] initWithArray:other.uninterpretedOptionArray];
+    } else {
+      [result.uninterpretedOptionArray addObjectsFromArray:other.uninterpretedOptionArray];
+    }
+  }
+  [self mergeExtensionFields:other];
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBMessageOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBMessageOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setMessageSetWireFormat:[input readBool]];
+        break;
+      }
+      case 16: {
+        [self setNoStandardDescriptorAccessor:[input readBool]];
+        break;
+      }
+      case 24: {
+        [self setDeprecated:[input readBool]];
+        break;
+      }
+      case 7994: {
+        PBUninterpretedOptionBuilder* subBuilder = [PBUninterpretedOption builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addUninterpretedOption:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasMessageSetWireFormat {
+  return result.hasMessageSetWireFormat;
+}
+- (BOOL) messageSetWireFormat {
+  return result.messageSetWireFormat;
+}
+- (PBMessageOptionsBuilder*) setMessageSetWireFormat:(BOOL) value {
+  result.hasMessageSetWireFormat = YES;
+  result.messageSetWireFormat = value;
+  return self;
+}
+- (PBMessageOptionsBuilder*) clearMessageSetWireFormat {
+  result.hasMessageSetWireFormat = NO;
+  result.messageSetWireFormat = NO;
+  return self;
+}
+- (BOOL) hasNoStandardDescriptorAccessor {
+  return result.hasNoStandardDescriptorAccessor;
+}
+- (BOOL) noStandardDescriptorAccessor {
+  return result.noStandardDescriptorAccessor;
+}
+- (PBMessageOptionsBuilder*) setNoStandardDescriptorAccessor:(BOOL) value {
+  result.hasNoStandardDescriptorAccessor = YES;
+  result.noStandardDescriptorAccessor = value;
+  return self;
+}
+- (PBMessageOptionsBuilder*) clearNoStandardDescriptorAccessor {
+  result.hasNoStandardDescriptorAccessor = NO;
+  result.noStandardDescriptorAccessor = NO;
+  return self;
+}
+- (BOOL) hasDeprecated {
+  return result.hasDeprecated;
+}
+- (BOOL) deprecated {
+  return result.deprecated;
+}
+- (PBMessageOptionsBuilder*) setDeprecated:(BOOL) value {
+  result.hasDeprecated = YES;
+  result.deprecated = value;
+  return self;
+}
+- (PBMessageOptionsBuilder*) clearDeprecated {
+  result.hasDeprecated = NO;
+  result.deprecated = NO;
+  return self;
+}
+- (NSMutableArray *)uninterpretedOption {
+  return result.uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [result uninterpretedOptionAtIndex:index];
+}
+- (PBMessageOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value {
+  if (result.uninterpretedOptionArray == nil) {
+    result.uninterpretedOptionArray = [[NSMutableArray alloc]init];
+  }
+  [result.uninterpretedOptionArray addObject:value];
+  return self;
+}
+- (PBMessageOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array {
+  result.uninterpretedOptionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBMessageOptionsBuilder *)clearUninterpretedOption {
+  result.uninterpretedOptionArray = nil;
+  return self;
+}
+@end
+
+@interface PBFieldOptions ()
+@property PBFieldOptionsCType ctype;
+@property BOOL packed;
+@property BOOL lazy;
+@property BOOL deprecated;
+@property (strong) NSString* experimentalMapKey;
+@property BOOL weak;
+@property (strong) NSMutableArray * uninterpretedOptionArray;
+@end
+
+@implementation PBFieldOptions
+
+- (BOOL) hasCtype {
+  return !!hasCtype_;
+}
+- (void) setHasCtype:(BOOL) value_ {
+  hasCtype_ = !!value_;
+}
+@synthesize ctype;
+- (BOOL) hasPacked {
+  return !!hasPacked_;
+}
+- (void) setHasPacked:(BOOL) value_ {
+  hasPacked_ = !!value_;
+}
+- (BOOL) packed {
+  return !!packed_;
+}
+- (void) setPacked:(BOOL) value_ {
+  packed_ = !!value_;
+}
+- (BOOL) hasLazy {
+  return !!hasLazy_;
+}
+- (void) setHasLazy:(BOOL) value_ {
+  hasLazy_ = !!value_;
+}
+- (BOOL) lazy {
+  return !!lazy_;
+}
+- (void) setLazy:(BOOL) value_ {
+  lazy_ = !!value_;
+}
+- (BOOL) hasDeprecated {
+  return !!hasDeprecated_;
+}
+- (void) setHasDeprecated:(BOOL) value_ {
+  hasDeprecated_ = !!value_;
+}
+- (BOOL) deprecated {
+  return !!deprecated_;
+}
+- (void) setDeprecated:(BOOL) value_ {
+  deprecated_ = !!value_;
+}
+- (BOOL) hasExperimentalMapKey {
+  return !!hasExperimentalMapKey_;
+}
+- (void) setHasExperimentalMapKey:(BOOL) value_ {
+  hasExperimentalMapKey_ = !!value_;
+}
+@synthesize experimentalMapKey;
+- (BOOL) hasWeak {
+  return !!hasWeak_;
+}
+- (void) setHasWeak:(BOOL) value_ {
+  hasWeak_ = !!value_;
+}
+- (BOOL) weak {
+  return !!weak_;
+}
+- (void) setWeak:(BOOL) value_ {
+  weak_ = !!value_;
+}
+@synthesize uninterpretedOptionArray;
+@dynamic uninterpretedOption;
+- (id) init {
+  if ((self = [super init])) {
+    self.ctype = PBFieldOptionsCTypeString;
+    self.packed = NO;
+    self.lazy = NO;
+    self.deprecated = NO;
+    self.experimentalMapKey = @"";
+    self.weak = NO;
+  }
+  return self;
+}
+static PBFieldOptions* defaultPBFieldOptionsInstance = nil;
++ (void) initialize {
+  if (self == [PBFieldOptions class]) {
+    defaultPBFieldOptionsInstance = [[PBFieldOptions alloc] init];
+  }
+}
++ (PBFieldOptions*) defaultInstance {
+  return defaultPBFieldOptionsInstance;
+}
+- (PBFieldOptions*) defaultInstance {
+  return defaultPBFieldOptionsInstance;
+}
+- (NSArray *)uninterpretedOption {
+  return uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [uninterpretedOptionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInituninterpretedOption = YES;
+   [self.uninterpretedOption enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInituninterpretedOption = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInituninterpretedOption) return isInituninterpretedOption;
+  if (!self.extensionsAreInitialized) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasCtype) {
+    [output writeEnum:1 value:self.ctype];
+  }
+  if (self.hasPacked) {
+    [output writeBool:2 value:self.packed];
+  }
+  if (self.hasDeprecated) {
+    [output writeBool:3 value:self.deprecated];
+  }
+  if (self.hasLazy) {
+    [output writeBool:5 value:self.lazy];
+  }
+  if (self.hasExperimentalMapKey) {
+    [output writeString:9 value:self.experimentalMapKey];
+  }
+  if (self.hasWeak) {
+    [output writeBool:10 value:self.weak];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:999 value:element];
+  }];
+  [self writeExtensionsToCodedOutputStream:output
+                                      from:1000
+                                        to:536870912];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasCtype) {
+    size_ += computeEnumSize(1, self.ctype);
+  }
+  if (self.hasPacked) {
+    size_ += computeBoolSize(2, self.packed);
+  }
+  if (self.hasDeprecated) {
+    size_ += computeBoolSize(3, self.deprecated);
+  }
+  if (self.hasLazy) {
+    size_ += computeBoolSize(5, self.lazy);
+  }
+  if (self.hasExperimentalMapKey) {
+    size_ += computeStringSize(9, self.experimentalMapKey);
+  }
+  if (self.hasWeak) {
+    size_ += computeBoolSize(10, self.weak);
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(999, element);
+  }];
+  size_ += [self extensionsSerializedSize];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBFieldOptions*) parseFromData:(NSData*) data {
+  return (PBFieldOptions*)[[[PBFieldOptions builder] mergeFromData:data] build];
+}
++ (PBFieldOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFieldOptions*)[[[PBFieldOptions builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBFieldOptions*) parseFromInputStream:(NSInputStream*) input {
+  return (PBFieldOptions*)[[[PBFieldOptions builder] mergeFromInputStream:input] build];
+}
++ (PBFieldOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFieldOptions*)[[[PBFieldOptions builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFieldOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBFieldOptions*)[[[PBFieldOptions builder] mergeFromCodedInputStream:input] build];
+}
++ (PBFieldOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBFieldOptions*)[[[PBFieldOptions builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBFieldOptionsBuilder*) builder {
+  return [[PBFieldOptionsBuilder alloc] init];
+}
++ (PBFieldOptionsBuilder*) builderWithPrototype:(PBFieldOptions*) prototype {
+  return [[PBFieldOptions builder] mergeFrom:prototype];
+}
+- (PBFieldOptionsBuilder*) builder {
+  return [PBFieldOptions builder];
+}
+- (PBFieldOptionsBuilder*) toBuilder {
+  return [PBFieldOptions builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasCtype) {
+    [output appendFormat:@"%@%@: %d\n", indent, @"ctype", self.ctype];
+  }
+  if (self.hasPacked) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"packed", [NSNumber numberWithBool:self.packed]];
+  }
+  if (self.hasDeprecated) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deprecated", [NSNumber numberWithBool:self.deprecated]];
+  }
+  if (self.hasLazy) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"lazy", [NSNumber numberWithBool:self.lazy]];
+  }
+  if (self.hasExperimentalMapKey) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"experimentalMapKey", self.experimentalMapKey];
+  }
+  if (self.hasWeak) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"weak", [NSNumber numberWithBool:self.weak]];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"uninterpretedOption"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self writeExtensionDescriptionToMutableString:(NSMutableString*)output
+                                            from:1000
+                                              to:536870912
+                                      withIndent:indent];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBFieldOptions class]]) {
+    return NO;
+  }
+  PBFieldOptions *otherMessage = other;
+  return
+      self.hasCtype == otherMessage.hasCtype &&
+      (!self.hasCtype || self.ctype == otherMessage.ctype) &&
+      self.hasPacked == otherMessage.hasPacked &&
+      (!self.hasPacked || self.packed == otherMessage.packed) &&
+      self.hasDeprecated == otherMessage.hasDeprecated &&
+      (!self.hasDeprecated || self.deprecated == otherMessage.deprecated) &&
+      self.hasLazy == otherMessage.hasLazy &&
+      (!self.hasLazy || self.lazy == otherMessage.lazy) &&
+      self.hasExperimentalMapKey == otherMessage.hasExperimentalMapKey &&
+      (!self.hasExperimentalMapKey || [self.experimentalMapKey isEqual:otherMessage.experimentalMapKey]) &&
+      self.hasWeak == otherMessage.hasWeak &&
+      (!self.hasWeak || self.weak == otherMessage.weak) &&
+      [self.uninterpretedOptionArray isEqualToArray:otherMessage.uninterpretedOptionArray] &&
+      [self isEqualExtensionsInOther:otherMessage from:1000 to:536870912] &&
+
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasCtype) {
+    hashCode = hashCode * 31 + self.ctype;
+  }
+  if (self.hasPacked) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.packed] hash];
+  }
+  if (self.hasDeprecated) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.deprecated] hash];
+  }
+  if (self.hasLazy) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.lazy] hash];
+  }
+  if (self.hasExperimentalMapKey) {
+    hashCode = hashCode * 31 + [self.experimentalMapKey hash];
+  }
+  if (self.hasWeak) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.weak] hash];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self hashExtensionsFrom:1000 to:536870912];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+BOOL PBFieldOptionsCTypeIsValidValue(PBFieldOptionsCType value) {
+  switch (value) {
+    case PBFieldOptionsCTypeString:
+    case PBFieldOptionsCTypeCord:
+    case PBFieldOptionsCTypeStringPiece:
+      return YES;
+    default:
+      return NO;
+  }
+}
+@interface PBFieldOptionsBuilder()
+@property (strong) PBFieldOptions* result;
+@end
+
+@implementation PBFieldOptionsBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBFieldOptions alloc] init];
+  }
+  return self;
+}
+- (PBExtendableMessage*) internalGetResult {
+  return result;
+}
+- (PBFieldOptionsBuilder*) clear {
+  self.result = [[PBFieldOptions alloc] init];
+  return self;
+}
+- (PBFieldOptionsBuilder*) clone {
+  return [PBFieldOptions builderWithPrototype:result];
+}
+- (PBFieldOptions*) defaultInstance {
+  return [PBFieldOptions defaultInstance];
+}
+- (PBFieldOptions*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBFieldOptions*) buildPartial {
+  PBFieldOptions* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBFieldOptionsBuilder*) mergeFrom:(PBFieldOptions*) other {
+  if (other == [PBFieldOptions defaultInstance]) {
+    return self;
+  }
+  if (other.hasCtype) {
+    [self setCtype:other.ctype];
+  }
+  if (other.hasPacked) {
+    [self setPacked:other.packed];
+  }
+  if (other.hasLazy) {
+    [self setLazy:other.lazy];
+  }
+  if (other.hasDeprecated) {
+    [self setDeprecated:other.deprecated];
+  }
+  if (other.hasExperimentalMapKey) {
+    [self setExperimentalMapKey:other.experimentalMapKey];
+  }
+  if (other.hasWeak) {
+    [self setWeak:other.weak];
+  }
+  if (other.uninterpretedOptionArray.count > 0) {
+    if (result.uninterpretedOptionArray == nil) {
+      result.uninterpretedOptionArray = [[NSMutableArray alloc] initWithArray:other.uninterpretedOptionArray];
+    } else {
+      [result.uninterpretedOptionArray addObjectsFromArray:other.uninterpretedOptionArray];
+    }
+  }
+  [self mergeExtensionFields:other];
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBFieldOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBFieldOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        PBFieldOptionsCType value = (PBFieldOptionsCType)[input readEnum];
+        if (PBFieldOptionsCTypeIsValidValue(value)) {
+          [self setCtype:value];
+        } else {
+          [unknownFields mergeVarintField:1 value:value];
+        }
+        break;
+      }
+      case 16: {
+        [self setPacked:[input readBool]];
+        break;
+      }
+      case 24: {
+        [self setDeprecated:[input readBool]];
+        break;
+      }
+      case 40: {
+        [self setLazy:[input readBool]];
+        break;
+      }
+      case 74: {
+        [self setExperimentalMapKey:[input readString]];
+        break;
+      }
+      case 80: {
+        [self setWeak:[input readBool]];
+        break;
+      }
+      case 7994: {
+        PBUninterpretedOptionBuilder* subBuilder = [PBUninterpretedOption builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addUninterpretedOption:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasCtype {
+  return result.hasCtype;
+}
+- (PBFieldOptionsCType) ctype {
+  return result.ctype;
+}
+- (PBFieldOptionsBuilder*) setCtype:(PBFieldOptionsCType) value {
+  result.hasCtype = YES;
+  result.ctype = value;
+  return self;
+}
+- (PBFieldOptionsBuilder*) clearCtype {
+  result.hasCtype = NO;
+  result.ctype = PBFieldOptionsCTypeString;
+  return self;
+}
+- (BOOL) hasPacked {
+  return result.hasPacked;
+}
+- (BOOL) packed {
+  return result.packed;
+}
+- (PBFieldOptionsBuilder*) setPacked:(BOOL) value {
+  result.hasPacked = YES;
+  result.packed = value;
+  return self;
+}
+- (PBFieldOptionsBuilder*) clearPacked {
+  result.hasPacked = NO;
+  result.packed = NO;
+  return self;
+}
+- (BOOL) hasLazy {
+  return result.hasLazy;
+}
+- (BOOL) lazy {
+  return result.lazy;
+}
+- (PBFieldOptionsBuilder*) setLazy:(BOOL) value {
+  result.hasLazy = YES;
+  result.lazy = value;
+  return self;
+}
+- (PBFieldOptionsBuilder*) clearLazy {
+  result.hasLazy = NO;
+  result.lazy = NO;
+  return self;
+}
+- (BOOL) hasDeprecated {
+  return result.hasDeprecated;
+}
+- (BOOL) deprecated {
+  return result.deprecated;
+}
+- (PBFieldOptionsBuilder*) setDeprecated:(BOOL) value {
+  result.hasDeprecated = YES;
+  result.deprecated = value;
+  return self;
+}
+- (PBFieldOptionsBuilder*) clearDeprecated {
+  result.hasDeprecated = NO;
+  result.deprecated = NO;
+  return self;
+}
+- (BOOL) hasExperimentalMapKey {
+  return result.hasExperimentalMapKey;
+}
+- (NSString*) experimentalMapKey {
+  return result.experimentalMapKey;
+}
+- (PBFieldOptionsBuilder*) setExperimentalMapKey:(NSString*) value {
+  result.hasExperimentalMapKey = YES;
+  result.experimentalMapKey = value;
+  return self;
+}
+- (PBFieldOptionsBuilder*) clearExperimentalMapKey {
+  result.hasExperimentalMapKey = NO;
+  result.experimentalMapKey = @"";
+  return self;
+}
+- (BOOL) hasWeak {
+  return result.hasWeak;
+}
+- (BOOL) weak {
+  return result.weak;
+}
+- (PBFieldOptionsBuilder*) setWeak:(BOOL) value {
+  result.hasWeak = YES;
+  result.weak = value;
+  return self;
+}
+- (PBFieldOptionsBuilder*) clearWeak {
+  result.hasWeak = NO;
+  result.weak = NO;
+  return self;
+}
+- (NSMutableArray *)uninterpretedOption {
+  return result.uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [result uninterpretedOptionAtIndex:index];
+}
+- (PBFieldOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value {
+  if (result.uninterpretedOptionArray == nil) {
+    result.uninterpretedOptionArray = [[NSMutableArray alloc]init];
+  }
+  [result.uninterpretedOptionArray addObject:value];
+  return self;
+}
+- (PBFieldOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array {
+  result.uninterpretedOptionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBFieldOptionsBuilder *)clearUninterpretedOption {
+  result.uninterpretedOptionArray = nil;
+  return self;
+}
+@end
+
+@interface PBEnumOptions ()
+@property BOOL allowAlias;
+@property BOOL deprecated;
+@property (strong) NSMutableArray * uninterpretedOptionArray;
+@end
+
+@implementation PBEnumOptions
+
+- (BOOL) hasAllowAlias {
+  return !!hasAllowAlias_;
+}
+- (void) setHasAllowAlias:(BOOL) value_ {
+  hasAllowAlias_ = !!value_;
+}
+- (BOOL) allowAlias {
+  return !!allowAlias_;
+}
+- (void) setAllowAlias:(BOOL) value_ {
+  allowAlias_ = !!value_;
+}
+- (BOOL) hasDeprecated {
+  return !!hasDeprecated_;
+}
+- (void) setHasDeprecated:(BOOL) value_ {
+  hasDeprecated_ = !!value_;
+}
+- (BOOL) deprecated {
+  return !!deprecated_;
+}
+- (void) setDeprecated:(BOOL) value_ {
+  deprecated_ = !!value_;
+}
+@synthesize uninterpretedOptionArray;
+@dynamic uninterpretedOption;
+- (id) init {
+  if ((self = [super init])) {
+    self.allowAlias = NO;
+    self.deprecated = NO;
+  }
+  return self;
+}
+static PBEnumOptions* defaultPBEnumOptionsInstance = nil;
++ (void) initialize {
+  if (self == [PBEnumOptions class]) {
+    defaultPBEnumOptionsInstance = [[PBEnumOptions alloc] init];
+  }
+}
++ (PBEnumOptions*) defaultInstance {
+  return defaultPBEnumOptionsInstance;
+}
+- (PBEnumOptions*) defaultInstance {
+  return defaultPBEnumOptionsInstance;
+}
+- (NSArray *)uninterpretedOption {
+  return uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [uninterpretedOptionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInituninterpretedOption = YES;
+   [self.uninterpretedOption enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInituninterpretedOption = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInituninterpretedOption) return isInituninterpretedOption;
+  if (!self.extensionsAreInitialized) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasAllowAlias) {
+    [output writeBool:2 value:self.allowAlias];
+  }
+  if (self.hasDeprecated) {
+    [output writeBool:3 value:self.deprecated];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:999 value:element];
+  }];
+  [self writeExtensionsToCodedOutputStream:output
+                                      from:1000
+                                        to:536870912];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasAllowAlias) {
+    size_ += computeBoolSize(2, self.allowAlias);
+  }
+  if (self.hasDeprecated) {
+    size_ += computeBoolSize(3, self.deprecated);
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(999, element);
+  }];
+  size_ += [self extensionsSerializedSize];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBEnumOptions*) parseFromData:(NSData*) data {
+  return (PBEnumOptions*)[[[PBEnumOptions builder] mergeFromData:data] build];
+}
++ (PBEnumOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumOptions*)[[[PBEnumOptions builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumOptions*) parseFromInputStream:(NSInputStream*) input {
+  return (PBEnumOptions*)[[[PBEnumOptions builder] mergeFromInputStream:input] build];
+}
++ (PBEnumOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumOptions*)[[[PBEnumOptions builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBEnumOptions*)[[[PBEnumOptions builder] mergeFromCodedInputStream:input] build];
+}
++ (PBEnumOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumOptions*)[[[PBEnumOptions builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumOptionsBuilder*) builder {
+  return [[PBEnumOptionsBuilder alloc] init];
+}
++ (PBEnumOptionsBuilder*) builderWithPrototype:(PBEnumOptions*) prototype {
+  return [[PBEnumOptions builder] mergeFrom:prototype];
+}
+- (PBEnumOptionsBuilder*) builder {
+  return [PBEnumOptions builder];
+}
+- (PBEnumOptionsBuilder*) toBuilder {
+  return [PBEnumOptions builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasAllowAlias) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"allowAlias", [NSNumber numberWithBool:self.allowAlias]];
+  }
+  if (self.hasDeprecated) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deprecated", [NSNumber numberWithBool:self.deprecated]];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"uninterpretedOption"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self writeExtensionDescriptionToMutableString:(NSMutableString*)output
+                                            from:1000
+                                              to:536870912
+                                      withIndent:indent];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBEnumOptions class]]) {
+    return NO;
+  }
+  PBEnumOptions *otherMessage = other;
+  return
+      self.hasAllowAlias == otherMessage.hasAllowAlias &&
+      (!self.hasAllowAlias || self.allowAlias == otherMessage.allowAlias) &&
+      self.hasDeprecated == otherMessage.hasDeprecated &&
+      (!self.hasDeprecated || self.deprecated == otherMessage.deprecated) &&
+      [self.uninterpretedOptionArray isEqualToArray:otherMessage.uninterpretedOptionArray] &&
+      [self isEqualExtensionsInOther:otherMessage from:1000 to:536870912] &&
+
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasAllowAlias) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.allowAlias] hash];
+  }
+  if (self.hasDeprecated) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.deprecated] hash];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self hashExtensionsFrom:1000 to:536870912];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBEnumOptionsBuilder()
+@property (strong) PBEnumOptions* result;
+@end
+
+@implementation PBEnumOptionsBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBEnumOptions alloc] init];
+  }
+  return self;
+}
+- (PBExtendableMessage*) internalGetResult {
+  return result;
+}
+- (PBEnumOptionsBuilder*) clear {
+  self.result = [[PBEnumOptions alloc] init];
+  return self;
+}
+- (PBEnumOptionsBuilder*) clone {
+  return [PBEnumOptions builderWithPrototype:result];
+}
+- (PBEnumOptions*) defaultInstance {
+  return [PBEnumOptions defaultInstance];
+}
+- (PBEnumOptions*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBEnumOptions*) buildPartial {
+  PBEnumOptions* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBEnumOptionsBuilder*) mergeFrom:(PBEnumOptions*) other {
+  if (other == [PBEnumOptions defaultInstance]) {
+    return self;
+  }
+  if (other.hasAllowAlias) {
+    [self setAllowAlias:other.allowAlias];
+  }
+  if (other.hasDeprecated) {
+    [self setDeprecated:other.deprecated];
+  }
+  if (other.uninterpretedOptionArray.count > 0) {
+    if (result.uninterpretedOptionArray == nil) {
+      result.uninterpretedOptionArray = [[NSMutableArray alloc] initWithArray:other.uninterpretedOptionArray];
+    } else {
+      [result.uninterpretedOptionArray addObjectsFromArray:other.uninterpretedOptionArray];
+    }
+  }
+  [self mergeExtensionFields:other];
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBEnumOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBEnumOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 16: {
+        [self setAllowAlias:[input readBool]];
+        break;
+      }
+      case 24: {
+        [self setDeprecated:[input readBool]];
+        break;
+      }
+      case 7994: {
+        PBUninterpretedOptionBuilder* subBuilder = [PBUninterpretedOption builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addUninterpretedOption:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasAllowAlias {
+  return result.hasAllowAlias;
+}
+- (BOOL) allowAlias {
+  return result.allowAlias;
+}
+- (PBEnumOptionsBuilder*) setAllowAlias:(BOOL) value {
+  result.hasAllowAlias = YES;
+  result.allowAlias = value;
+  return self;
+}
+- (PBEnumOptionsBuilder*) clearAllowAlias {
+  result.hasAllowAlias = NO;
+  result.allowAlias = NO;
+  return self;
+}
+- (BOOL) hasDeprecated {
+  return result.hasDeprecated;
+}
+- (BOOL) deprecated {
+  return result.deprecated;
+}
+- (PBEnumOptionsBuilder*) setDeprecated:(BOOL) value {
+  result.hasDeprecated = YES;
+  result.deprecated = value;
+  return self;
+}
+- (PBEnumOptionsBuilder*) clearDeprecated {
+  result.hasDeprecated = NO;
+  result.deprecated = NO;
+  return self;
+}
+- (NSMutableArray *)uninterpretedOption {
+  return result.uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [result uninterpretedOptionAtIndex:index];
+}
+- (PBEnumOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value {
+  if (result.uninterpretedOptionArray == nil) {
+    result.uninterpretedOptionArray = [[NSMutableArray alloc]init];
+  }
+  [result.uninterpretedOptionArray addObject:value];
+  return self;
+}
+- (PBEnumOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array {
+  result.uninterpretedOptionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBEnumOptionsBuilder *)clearUninterpretedOption {
+  result.uninterpretedOptionArray = nil;
+  return self;
+}
+@end
+
+@interface PBEnumValueOptions ()
+@property BOOL deprecated;
+@property (strong) NSMutableArray * uninterpretedOptionArray;
+@end
+
+@implementation PBEnumValueOptions
+
+- (BOOL) hasDeprecated {
+  return !!hasDeprecated_;
+}
+- (void) setHasDeprecated:(BOOL) value_ {
+  hasDeprecated_ = !!value_;
+}
+- (BOOL) deprecated {
+  return !!deprecated_;
+}
+- (void) setDeprecated:(BOOL) value_ {
+  deprecated_ = !!value_;
+}
+@synthesize uninterpretedOptionArray;
+@dynamic uninterpretedOption;
+- (id) init {
+  if ((self = [super init])) {
+    self.deprecated = NO;
+  }
+  return self;
+}
+static PBEnumValueOptions* defaultPBEnumValueOptionsInstance = nil;
++ (void) initialize {
+  if (self == [PBEnumValueOptions class]) {
+    defaultPBEnumValueOptionsInstance = [[PBEnumValueOptions alloc] init];
+  }
+}
++ (PBEnumValueOptions*) defaultInstance {
+  return defaultPBEnumValueOptionsInstance;
+}
+- (PBEnumValueOptions*) defaultInstance {
+  return defaultPBEnumValueOptionsInstance;
+}
+- (NSArray *)uninterpretedOption {
+  return uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [uninterpretedOptionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInituninterpretedOption = YES;
+   [self.uninterpretedOption enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInituninterpretedOption = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInituninterpretedOption) return isInituninterpretedOption;
+  if (!self.extensionsAreInitialized) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasDeprecated) {
+    [output writeBool:1 value:self.deprecated];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:999 value:element];
+  }];
+  [self writeExtensionsToCodedOutputStream:output
+                                      from:1000
+                                        to:536870912];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasDeprecated) {
+    size_ += computeBoolSize(1, self.deprecated);
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(999, element);
+  }];
+  size_ += [self extensionsSerializedSize];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBEnumValueOptions*) parseFromData:(NSData*) data {
+  return (PBEnumValueOptions*)[[[PBEnumValueOptions builder] mergeFromData:data] build];
+}
++ (PBEnumValueOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumValueOptions*)[[[PBEnumValueOptions builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumValueOptions*) parseFromInputStream:(NSInputStream*) input {
+  return (PBEnumValueOptions*)[[[PBEnumValueOptions builder] mergeFromInputStream:input] build];
+}
++ (PBEnumValueOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumValueOptions*)[[[PBEnumValueOptions builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumValueOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBEnumValueOptions*)[[[PBEnumValueOptions builder] mergeFromCodedInputStream:input] build];
+}
++ (PBEnumValueOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBEnumValueOptions*)[[[PBEnumValueOptions builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBEnumValueOptionsBuilder*) builder {
+  return [[PBEnumValueOptionsBuilder alloc] init];
+}
++ (PBEnumValueOptionsBuilder*) builderWithPrototype:(PBEnumValueOptions*) prototype {
+  return [[PBEnumValueOptions builder] mergeFrom:prototype];
+}
+- (PBEnumValueOptionsBuilder*) builder {
+  return [PBEnumValueOptions builder];
+}
+- (PBEnumValueOptionsBuilder*) toBuilder {
+  return [PBEnumValueOptions builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasDeprecated) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deprecated", [NSNumber numberWithBool:self.deprecated]];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"uninterpretedOption"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self writeExtensionDescriptionToMutableString:(NSMutableString*)output
+                                            from:1000
+                                              to:536870912
+                                      withIndent:indent];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBEnumValueOptions class]]) {
+    return NO;
+  }
+  PBEnumValueOptions *otherMessage = other;
+  return
+      self.hasDeprecated == otherMessage.hasDeprecated &&
+      (!self.hasDeprecated || self.deprecated == otherMessage.deprecated) &&
+      [self.uninterpretedOptionArray isEqualToArray:otherMessage.uninterpretedOptionArray] &&
+      [self isEqualExtensionsInOther:otherMessage from:1000 to:536870912] &&
+
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasDeprecated) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.deprecated] hash];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self hashExtensionsFrom:1000 to:536870912];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBEnumValueOptionsBuilder()
+@property (strong) PBEnumValueOptions* result;
+@end
+
+@implementation PBEnumValueOptionsBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBEnumValueOptions alloc] init];
+  }
+  return self;
+}
+- (PBExtendableMessage*) internalGetResult {
+  return result;
+}
+- (PBEnumValueOptionsBuilder*) clear {
+  self.result = [[PBEnumValueOptions alloc] init];
+  return self;
+}
+- (PBEnumValueOptionsBuilder*) clone {
+  return [PBEnumValueOptions builderWithPrototype:result];
+}
+- (PBEnumValueOptions*) defaultInstance {
+  return [PBEnumValueOptions defaultInstance];
+}
+- (PBEnumValueOptions*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBEnumValueOptions*) buildPartial {
+  PBEnumValueOptions* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBEnumValueOptionsBuilder*) mergeFrom:(PBEnumValueOptions*) other {
+  if (other == [PBEnumValueOptions defaultInstance]) {
+    return self;
+  }
+  if (other.hasDeprecated) {
+    [self setDeprecated:other.deprecated];
+  }
+  if (other.uninterpretedOptionArray.count > 0) {
+    if (result.uninterpretedOptionArray == nil) {
+      result.uninterpretedOptionArray = [[NSMutableArray alloc] initWithArray:other.uninterpretedOptionArray];
+    } else {
+      [result.uninterpretedOptionArray addObjectsFromArray:other.uninterpretedOptionArray];
+    }
+  }
+  [self mergeExtensionFields:other];
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBEnumValueOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBEnumValueOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 8: {
+        [self setDeprecated:[input readBool]];
+        break;
+      }
+      case 7994: {
+        PBUninterpretedOptionBuilder* subBuilder = [PBUninterpretedOption builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addUninterpretedOption:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasDeprecated {
+  return result.hasDeprecated;
+}
+- (BOOL) deprecated {
+  return result.deprecated;
+}
+- (PBEnumValueOptionsBuilder*) setDeprecated:(BOOL) value {
+  result.hasDeprecated = YES;
+  result.deprecated = value;
+  return self;
+}
+- (PBEnumValueOptionsBuilder*) clearDeprecated {
+  result.hasDeprecated = NO;
+  result.deprecated = NO;
+  return self;
+}
+- (NSMutableArray *)uninterpretedOption {
+  return result.uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [result uninterpretedOptionAtIndex:index];
+}
+- (PBEnumValueOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value {
+  if (result.uninterpretedOptionArray == nil) {
+    result.uninterpretedOptionArray = [[NSMutableArray alloc]init];
+  }
+  [result.uninterpretedOptionArray addObject:value];
+  return self;
+}
+- (PBEnumValueOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array {
+  result.uninterpretedOptionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBEnumValueOptionsBuilder *)clearUninterpretedOption {
+  result.uninterpretedOptionArray = nil;
+  return self;
+}
+@end
+
+@interface PBServiceOptions ()
+@property BOOL deprecated;
+@property (strong) NSMutableArray * uninterpretedOptionArray;
+@end
+
+@implementation PBServiceOptions
+
+- (BOOL) hasDeprecated {
+  return !!hasDeprecated_;
+}
+- (void) setHasDeprecated:(BOOL) value_ {
+  hasDeprecated_ = !!value_;
+}
+- (BOOL) deprecated {
+  return !!deprecated_;
+}
+- (void) setDeprecated:(BOOL) value_ {
+  deprecated_ = !!value_;
+}
+@synthesize uninterpretedOptionArray;
+@dynamic uninterpretedOption;
+- (id) init {
+  if ((self = [super init])) {
+    self.deprecated = NO;
+  }
+  return self;
+}
+static PBServiceOptions* defaultPBServiceOptionsInstance = nil;
++ (void) initialize {
+  if (self == [PBServiceOptions class]) {
+    defaultPBServiceOptionsInstance = [[PBServiceOptions alloc] init];
+  }
+}
++ (PBServiceOptions*) defaultInstance {
+  return defaultPBServiceOptionsInstance;
+}
+- (PBServiceOptions*) defaultInstance {
+  return defaultPBServiceOptionsInstance;
+}
+- (NSArray *)uninterpretedOption {
+  return uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [uninterpretedOptionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInituninterpretedOption = YES;
+   [self.uninterpretedOption enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInituninterpretedOption = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInituninterpretedOption) return isInituninterpretedOption;
+  if (!self.extensionsAreInitialized) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasDeprecated) {
+    [output writeBool:33 value:self.deprecated];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:999 value:element];
+  }];
+  [self writeExtensionsToCodedOutputStream:output
+                                      from:1000
+                                        to:536870912];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasDeprecated) {
+    size_ += computeBoolSize(33, self.deprecated);
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(999, element);
+  }];
+  size_ += [self extensionsSerializedSize];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBServiceOptions*) parseFromData:(NSData*) data {
+  return (PBServiceOptions*)[[[PBServiceOptions builder] mergeFromData:data] build];
+}
++ (PBServiceOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBServiceOptions*)[[[PBServiceOptions builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBServiceOptions*) parseFromInputStream:(NSInputStream*) input {
+  return (PBServiceOptions*)[[[PBServiceOptions builder] mergeFromInputStream:input] build];
+}
++ (PBServiceOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBServiceOptions*)[[[PBServiceOptions builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBServiceOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBServiceOptions*)[[[PBServiceOptions builder] mergeFromCodedInputStream:input] build];
+}
++ (PBServiceOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBServiceOptions*)[[[PBServiceOptions builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBServiceOptionsBuilder*) builder {
+  return [[PBServiceOptionsBuilder alloc] init];
+}
++ (PBServiceOptionsBuilder*) builderWithPrototype:(PBServiceOptions*) prototype {
+  return [[PBServiceOptions builder] mergeFrom:prototype];
+}
+- (PBServiceOptionsBuilder*) builder {
+  return [PBServiceOptions builder];
+}
+- (PBServiceOptionsBuilder*) toBuilder {
+  return [PBServiceOptions builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasDeprecated) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deprecated", [NSNumber numberWithBool:self.deprecated]];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"uninterpretedOption"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self writeExtensionDescriptionToMutableString:(NSMutableString*)output
+                                            from:1000
+                                              to:536870912
+                                      withIndent:indent];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBServiceOptions class]]) {
+    return NO;
+  }
+  PBServiceOptions *otherMessage = other;
+  return
+      self.hasDeprecated == otherMessage.hasDeprecated &&
+      (!self.hasDeprecated || self.deprecated == otherMessage.deprecated) &&
+      [self.uninterpretedOptionArray isEqualToArray:otherMessage.uninterpretedOptionArray] &&
+      [self isEqualExtensionsInOther:otherMessage from:1000 to:536870912] &&
+
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasDeprecated) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.deprecated] hash];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self hashExtensionsFrom:1000 to:536870912];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBServiceOptionsBuilder()
+@property (strong) PBServiceOptions* result;
+@end
+
+@implementation PBServiceOptionsBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBServiceOptions alloc] init];
+  }
+  return self;
+}
+- (PBExtendableMessage*) internalGetResult {
+  return result;
+}
+- (PBServiceOptionsBuilder*) clear {
+  self.result = [[PBServiceOptions alloc] init];
+  return self;
+}
+- (PBServiceOptionsBuilder*) clone {
+  return [PBServiceOptions builderWithPrototype:result];
+}
+- (PBServiceOptions*) defaultInstance {
+  return [PBServiceOptions defaultInstance];
+}
+- (PBServiceOptions*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBServiceOptions*) buildPartial {
+  PBServiceOptions* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBServiceOptionsBuilder*) mergeFrom:(PBServiceOptions*) other {
+  if (other == [PBServiceOptions defaultInstance]) {
+    return self;
+  }
+  if (other.hasDeprecated) {
+    [self setDeprecated:other.deprecated];
+  }
+  if (other.uninterpretedOptionArray.count > 0) {
+    if (result.uninterpretedOptionArray == nil) {
+      result.uninterpretedOptionArray = [[NSMutableArray alloc] initWithArray:other.uninterpretedOptionArray];
+    } else {
+      [result.uninterpretedOptionArray addObjectsFromArray:other.uninterpretedOptionArray];
+    }
+  }
+  [self mergeExtensionFields:other];
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBServiceOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBServiceOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 264: {
+        [self setDeprecated:[input readBool]];
+        break;
+      }
+      case 7994: {
+        PBUninterpretedOptionBuilder* subBuilder = [PBUninterpretedOption builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addUninterpretedOption:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasDeprecated {
+  return result.hasDeprecated;
+}
+- (BOOL) deprecated {
+  return result.deprecated;
+}
+- (PBServiceOptionsBuilder*) setDeprecated:(BOOL) value {
+  result.hasDeprecated = YES;
+  result.deprecated = value;
+  return self;
+}
+- (PBServiceOptionsBuilder*) clearDeprecated {
+  result.hasDeprecated = NO;
+  result.deprecated = NO;
+  return self;
+}
+- (NSMutableArray *)uninterpretedOption {
+  return result.uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [result uninterpretedOptionAtIndex:index];
+}
+- (PBServiceOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value {
+  if (result.uninterpretedOptionArray == nil) {
+    result.uninterpretedOptionArray = [[NSMutableArray alloc]init];
+  }
+  [result.uninterpretedOptionArray addObject:value];
+  return self;
+}
+- (PBServiceOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array {
+  result.uninterpretedOptionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBServiceOptionsBuilder *)clearUninterpretedOption {
+  result.uninterpretedOptionArray = nil;
+  return self;
+}
+@end
+
+@interface PBMethodOptions ()
+@property BOOL deprecated;
+@property (strong) NSMutableArray * uninterpretedOptionArray;
+@end
+
+@implementation PBMethodOptions
+
+- (BOOL) hasDeprecated {
+  return !!hasDeprecated_;
+}
+- (void) setHasDeprecated:(BOOL) value_ {
+  hasDeprecated_ = !!value_;
+}
+- (BOOL) deprecated {
+  return !!deprecated_;
+}
+- (void) setDeprecated:(BOOL) value_ {
+  deprecated_ = !!value_;
+}
+@synthesize uninterpretedOptionArray;
+@dynamic uninterpretedOption;
+- (id) init {
+  if ((self = [super init])) {
+    self.deprecated = NO;
+  }
+  return self;
+}
+static PBMethodOptions* defaultPBMethodOptionsInstance = nil;
++ (void) initialize {
+  if (self == [PBMethodOptions class]) {
+    defaultPBMethodOptionsInstance = [[PBMethodOptions alloc] init];
+  }
+}
++ (PBMethodOptions*) defaultInstance {
+  return defaultPBMethodOptionsInstance;
+}
+- (PBMethodOptions*) defaultInstance {
+  return defaultPBMethodOptionsInstance;
+}
+- (NSArray *)uninterpretedOption {
+  return uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [uninterpretedOptionArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInituninterpretedOption = YES;
+   [self.uninterpretedOption enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInituninterpretedOption = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInituninterpretedOption) return isInituninterpretedOption;
+  if (!self.extensionsAreInitialized) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasDeprecated) {
+    [output writeBool:33 value:self.deprecated];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:999 value:element];
+  }];
+  [self writeExtensionsToCodedOutputStream:output
+                                      from:1000
+                                        to:536870912];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasDeprecated) {
+    size_ += computeBoolSize(33, self.deprecated);
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(999, element);
+  }];
+  size_ += [self extensionsSerializedSize];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBMethodOptions*) parseFromData:(NSData*) data {
+  return (PBMethodOptions*)[[[PBMethodOptions builder] mergeFromData:data] build];
+}
++ (PBMethodOptions*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMethodOptions*)[[[PBMethodOptions builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBMethodOptions*) parseFromInputStream:(NSInputStream*) input {
+  return (PBMethodOptions*)[[[PBMethodOptions builder] mergeFromInputStream:input] build];
+}
++ (PBMethodOptions*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMethodOptions*)[[[PBMethodOptions builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBMethodOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBMethodOptions*)[[[PBMethodOptions builder] mergeFromCodedInputStream:input] build];
+}
++ (PBMethodOptions*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBMethodOptions*)[[[PBMethodOptions builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBMethodOptionsBuilder*) builder {
+  return [[PBMethodOptionsBuilder alloc] init];
+}
++ (PBMethodOptionsBuilder*) builderWithPrototype:(PBMethodOptions*) prototype {
+  return [[PBMethodOptions builder] mergeFrom:prototype];
+}
+- (PBMethodOptionsBuilder*) builder {
+  return [PBMethodOptions builder];
+}
+- (PBMethodOptionsBuilder*) toBuilder {
+  return [PBMethodOptions builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasDeprecated) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"deprecated", [NSNumber numberWithBool:self.deprecated]];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"uninterpretedOption"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self writeExtensionDescriptionToMutableString:(NSMutableString*)output
+                                            from:1000
+                                              to:536870912
+                                      withIndent:indent];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBMethodOptions class]]) {
+    return NO;
+  }
+  PBMethodOptions *otherMessage = other;
+  return
+      self.hasDeprecated == otherMessage.hasDeprecated &&
+      (!self.hasDeprecated || self.deprecated == otherMessage.deprecated) &&
+      [self.uninterpretedOptionArray isEqualToArray:otherMessage.uninterpretedOptionArray] &&
+      [self isEqualExtensionsInOther:otherMessage from:1000 to:536870912] &&
+
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasDeprecated) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.deprecated] hash];
+  }
+  [self.uninterpretedOptionArray enumerateObjectsUsingBlock:^(PBUninterpretedOption *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self hashExtensionsFrom:1000 to:536870912];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBMethodOptionsBuilder()
+@property (strong) PBMethodOptions* result;
+@end
+
+@implementation PBMethodOptionsBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBMethodOptions alloc] init];
+  }
+  return self;
+}
+- (PBExtendableMessage*) internalGetResult {
+  return result;
+}
+- (PBMethodOptionsBuilder*) clear {
+  self.result = [[PBMethodOptions alloc] init];
+  return self;
+}
+- (PBMethodOptionsBuilder*) clone {
+  return [PBMethodOptions builderWithPrototype:result];
+}
+- (PBMethodOptions*) defaultInstance {
+  return [PBMethodOptions defaultInstance];
+}
+- (PBMethodOptions*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBMethodOptions*) buildPartial {
+  PBMethodOptions* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBMethodOptionsBuilder*) mergeFrom:(PBMethodOptions*) other {
+  if (other == [PBMethodOptions defaultInstance]) {
+    return self;
+  }
+  if (other.hasDeprecated) {
+    [self setDeprecated:other.deprecated];
+  }
+  if (other.uninterpretedOptionArray.count > 0) {
+    if (result.uninterpretedOptionArray == nil) {
+      result.uninterpretedOptionArray = [[NSMutableArray alloc] initWithArray:other.uninterpretedOptionArray];
+    } else {
+      [result.uninterpretedOptionArray addObjectsFromArray:other.uninterpretedOptionArray];
+    }
+  }
+  [self mergeExtensionFields:other];
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBMethodOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBMethodOptionsBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 264: {
+        [self setDeprecated:[input readBool]];
+        break;
+      }
+      case 7994: {
+        PBUninterpretedOptionBuilder* subBuilder = [PBUninterpretedOption builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addUninterpretedOption:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasDeprecated {
+  return result.hasDeprecated;
+}
+- (BOOL) deprecated {
+  return result.deprecated;
+}
+- (PBMethodOptionsBuilder*) setDeprecated:(BOOL) value {
+  result.hasDeprecated = YES;
+  result.deprecated = value;
+  return self;
+}
+- (PBMethodOptionsBuilder*) clearDeprecated {
+  result.hasDeprecated = NO;
+  result.deprecated = NO;
+  return self;
+}
+- (NSMutableArray *)uninterpretedOption {
+  return result.uninterpretedOptionArray;
+}
+- (PBUninterpretedOption*)uninterpretedOptionAtIndex:(NSUInteger)index {
+  return [result uninterpretedOptionAtIndex:index];
+}
+- (PBMethodOptionsBuilder *)addUninterpretedOption:(PBUninterpretedOption*)value {
+  if (result.uninterpretedOptionArray == nil) {
+    result.uninterpretedOptionArray = [[NSMutableArray alloc]init];
+  }
+  [result.uninterpretedOptionArray addObject:value];
+  return self;
+}
+- (PBMethodOptionsBuilder *)setUninterpretedOptionArray:(NSArray *)array {
+  result.uninterpretedOptionArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBMethodOptionsBuilder *)clearUninterpretedOption {
+  result.uninterpretedOptionArray = nil;
+  return self;
+}
+@end
+
+@interface PBUninterpretedOption ()
+@property (strong) NSMutableArray * nameArray;
+@property (strong) NSString* identifierValue;
+@property UInt64 positiveIntValue;
+@property SInt64 negativeIntValue;
+@property Float64 doubleValue;
+@property (strong) NSData* stringValue;
+@property (strong) NSString* aggregateValue;
+@end
+
+@implementation PBUninterpretedOption
+
+@synthesize nameArray;
+@dynamic name;
+- (BOOL) hasIdentifierValue {
+  return !!hasIdentifierValue_;
+}
+- (void) setHasIdentifierValue:(BOOL) value_ {
+  hasIdentifierValue_ = !!value_;
+}
+@synthesize identifierValue;
+- (BOOL) hasPositiveIntValue {
+  return !!hasPositiveIntValue_;
+}
+- (void) setHasPositiveIntValue:(BOOL) value_ {
+  hasPositiveIntValue_ = !!value_;
+}
+@synthesize positiveIntValue;
+- (BOOL) hasNegativeIntValue {
+  return !!hasNegativeIntValue_;
+}
+- (void) setHasNegativeIntValue:(BOOL) value_ {
+  hasNegativeIntValue_ = !!value_;
+}
+@synthesize negativeIntValue;
+- (BOOL) hasDoubleValue {
+  return !!hasDoubleValue_;
+}
+- (void) setHasDoubleValue:(BOOL) value_ {
+  hasDoubleValue_ = !!value_;
+}
+@synthesize doubleValue;
+- (BOOL) hasStringValue {
+  return !!hasStringValue_;
+}
+- (void) setHasStringValue:(BOOL) value_ {
+  hasStringValue_ = !!value_;
+}
+@synthesize stringValue;
+- (BOOL) hasAggregateValue {
+  return !!hasAggregateValue_;
+}
+- (void) setHasAggregateValue:(BOOL) value_ {
+  hasAggregateValue_ = !!value_;
+}
+@synthesize aggregateValue;
+- (id) init {
+  if ((self = [super init])) {
+    self.identifierValue = @"";
+    self.positiveIntValue = 0L;
+    self.negativeIntValue = 0L;
+    self.doubleValue = 0;
+    self.stringValue = [NSData data];
+    self.aggregateValue = @"";
+  }
+  return self;
+}
+static PBUninterpretedOption* defaultPBUninterpretedOptionInstance = nil;
++ (void) initialize {
+  if (self == [PBUninterpretedOption class]) {
+    defaultPBUninterpretedOptionInstance = [[PBUninterpretedOption alloc] init];
+  }
+}
++ (PBUninterpretedOption*) defaultInstance {
+  return defaultPBUninterpretedOptionInstance;
+}
+- (PBUninterpretedOption*) defaultInstance {
+  return defaultPBUninterpretedOptionInstance;
+}
+- (NSArray *)name {
+  return nameArray;
+}
+- (PBUninterpretedOptionNamePart*)nameAtIndex:(NSUInteger)index {
+  return [nameArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  __block BOOL isInitname = YES;
+   [self.name enumerateObjectsUsingBlock:^(PBUninterpretedOptionNamePart *element, NSUInteger idx, BOOL *stop) {
+    if (!element.isInitialized) {
+      isInitname = NO;
+      *stop = YES;
+    }
+  }];
+  if (!isInitname) return isInitname;
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  [self.nameArray enumerateObjectsUsingBlock:^(PBUninterpretedOptionNamePart *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:2 value:element];
+  }];
+  if (self.hasIdentifierValue) {
+    [output writeString:3 value:self.identifierValue];
+  }
+  if (self.hasPositiveIntValue) {
+    [output writeUInt64:4 value:self.positiveIntValue];
+  }
+  if (self.hasNegativeIntValue) {
+    [output writeInt64:5 value:self.negativeIntValue];
+  }
+  if (self.hasDoubleValue) {
+    [output writeDouble:6 value:self.doubleValue];
+  }
+  if (self.hasStringValue) {
+    [output writeData:7 value:self.stringValue];
+  }
+  if (self.hasAggregateValue) {
+    [output writeString:8 value:self.aggregateValue];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  [self.nameArray enumerateObjectsUsingBlock:^(PBUninterpretedOptionNamePart *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(2, element);
+  }];
+  if (self.hasIdentifierValue) {
+    size_ += computeStringSize(3, self.identifierValue);
+  }
+  if (self.hasPositiveIntValue) {
+    size_ += computeUInt64Size(4, self.positiveIntValue);
+  }
+  if (self.hasNegativeIntValue) {
+    size_ += computeInt64Size(5, self.negativeIntValue);
+  }
+  if (self.hasDoubleValue) {
+    size_ += computeDoubleSize(6, self.doubleValue);
+  }
+  if (self.hasStringValue) {
+    size_ += computeDataSize(7, self.stringValue);
+  }
+  if (self.hasAggregateValue) {
+    size_ += computeStringSize(8, self.aggregateValue);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBUninterpretedOption*) parseFromData:(NSData*) data {
+  return (PBUninterpretedOption*)[[[PBUninterpretedOption builder] mergeFromData:data] build];
+}
++ (PBUninterpretedOption*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBUninterpretedOption*)[[[PBUninterpretedOption builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBUninterpretedOption*) parseFromInputStream:(NSInputStream*) input {
+  return (PBUninterpretedOption*)[[[PBUninterpretedOption builder] mergeFromInputStream:input] build];
+}
++ (PBUninterpretedOption*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBUninterpretedOption*)[[[PBUninterpretedOption builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBUninterpretedOption*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBUninterpretedOption*)[[[PBUninterpretedOption builder] mergeFromCodedInputStream:input] build];
+}
++ (PBUninterpretedOption*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBUninterpretedOption*)[[[PBUninterpretedOption builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBUninterpretedOptionBuilder*) builder {
+  return [[PBUninterpretedOptionBuilder alloc] init];
+}
++ (PBUninterpretedOptionBuilder*) builderWithPrototype:(PBUninterpretedOption*) prototype {
+  return [[PBUninterpretedOption builder] mergeFrom:prototype];
+}
+- (PBUninterpretedOptionBuilder*) builder {
+  return [PBUninterpretedOption builder];
+}
+- (PBUninterpretedOptionBuilder*) toBuilder {
+  return [PBUninterpretedOption builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.nameArray enumerateObjectsUsingBlock:^(PBUninterpretedOptionNamePart *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"name"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  if (self.hasIdentifierValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"identifierValue", self.identifierValue];
+  }
+  if (self.hasPositiveIntValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"positiveIntValue", [NSNumber numberWithLongLong:self.positiveIntValue]];
+  }
+  if (self.hasNegativeIntValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"negativeIntValue", [NSNumber numberWithLongLong:self.negativeIntValue]];
+  }
+  if (self.hasDoubleValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"doubleValue", [NSNumber numberWithDouble:self.doubleValue]];
+  }
+  if (self.hasStringValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"stringValue", self.stringValue];
+  }
+  if (self.hasAggregateValue) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"aggregateValue", self.aggregateValue];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBUninterpretedOption class]]) {
+    return NO;
+  }
+  PBUninterpretedOption *otherMessage = other;
+  return
+      [self.nameArray isEqualToArray:otherMessage.nameArray] &&
+      self.hasIdentifierValue == otherMessage.hasIdentifierValue &&
+      (!self.hasIdentifierValue || [self.identifierValue isEqual:otherMessage.identifierValue]) &&
+      self.hasPositiveIntValue == otherMessage.hasPositiveIntValue &&
+      (!self.hasPositiveIntValue || self.positiveIntValue == otherMessage.positiveIntValue) &&
+      self.hasNegativeIntValue == otherMessage.hasNegativeIntValue &&
+      (!self.hasNegativeIntValue || self.negativeIntValue == otherMessage.negativeIntValue) &&
+      self.hasDoubleValue == otherMessage.hasDoubleValue &&
+      (!self.hasDoubleValue || self.doubleValue == otherMessage.doubleValue) &&
+      self.hasStringValue == otherMessage.hasStringValue &&
+      (!self.hasStringValue || [self.stringValue isEqual:otherMessage.stringValue]) &&
+      self.hasAggregateValue == otherMessage.hasAggregateValue &&
+      (!self.hasAggregateValue || [self.aggregateValue isEqual:otherMessage.aggregateValue]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  [self.nameArray enumerateObjectsUsingBlock:^(PBUninterpretedOptionNamePart *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  if (self.hasIdentifierValue) {
+    hashCode = hashCode * 31 + [self.identifierValue hash];
+  }
+  if (self.hasPositiveIntValue) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.positiveIntValue] hash];
+  }
+  if (self.hasNegativeIntValue) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithLongLong:self.negativeIntValue] hash];
+  }
+  if (self.hasDoubleValue) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithDouble:self.doubleValue] hash];
+  }
+  if (self.hasStringValue) {
+    hashCode = hashCode * 31 + [self.stringValue hash];
+  }
+  if (self.hasAggregateValue) {
+    hashCode = hashCode * 31 + [self.aggregateValue hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBUninterpretedOptionNamePart ()
+@property (strong) NSString* namePart;
+@property BOOL isExtension;
+@end
+
+@implementation PBUninterpretedOptionNamePart
+
+- (BOOL) hasNamePart {
+  return !!hasNamePart_;
+}
+- (void) setHasNamePart:(BOOL) value_ {
+  hasNamePart_ = !!value_;
+}
+@synthesize namePart;
+- (BOOL) hasIsExtension {
+  return !!hasIsExtension_;
+}
+- (void) setHasIsExtension:(BOOL) value_ {
+  hasIsExtension_ = !!value_;
+}
+- (BOOL) isExtension {
+  return !!isExtension_;
+}
+- (void) setIsExtension:(BOOL) value_ {
+  isExtension_ = !!value_;
+}
+- (id) init {
+  if ((self = [super init])) {
+    self.namePart = @"";
+    self.isExtension = NO;
+  }
+  return self;
+}
+static PBUninterpretedOptionNamePart* defaultPBUninterpretedOptionNamePartInstance = nil;
++ (void) initialize {
+  if (self == [PBUninterpretedOptionNamePart class]) {
+    defaultPBUninterpretedOptionNamePartInstance = [[PBUninterpretedOptionNamePart alloc] init];
+  }
+}
++ (PBUninterpretedOptionNamePart*) defaultInstance {
+  return defaultPBUninterpretedOptionNamePartInstance;
+}
+- (PBUninterpretedOptionNamePart*) defaultInstance {
+  return defaultPBUninterpretedOptionNamePartInstance;
+}
+- (BOOL) isInitialized {
+  if (!self.hasNamePart) {
+    return NO;
+  }
+  if (!self.hasIsExtension) {
+    return NO;
+  }
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  if (self.hasNamePart) {
+    [output writeString:1 value:self.namePart];
+  }
+  if (self.hasIsExtension) {
+    [output writeBool:2 value:self.isExtension];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  if (self.hasNamePart) {
+    size_ += computeStringSize(1, self.namePart);
+  }
+  if (self.hasIsExtension) {
+    size_ += computeBoolSize(2, self.isExtension);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBUninterpretedOptionNamePart*) parseFromData:(NSData*) data {
+  return (PBUninterpretedOptionNamePart*)[[[PBUninterpretedOptionNamePart builder] mergeFromData:data] build];
+}
++ (PBUninterpretedOptionNamePart*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBUninterpretedOptionNamePart*)[[[PBUninterpretedOptionNamePart builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBUninterpretedOptionNamePart*) parseFromInputStream:(NSInputStream*) input {
+  return (PBUninterpretedOptionNamePart*)[[[PBUninterpretedOptionNamePart builder] mergeFromInputStream:input] build];
+}
++ (PBUninterpretedOptionNamePart*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBUninterpretedOptionNamePart*)[[[PBUninterpretedOptionNamePart builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBUninterpretedOptionNamePart*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBUninterpretedOptionNamePart*)[[[PBUninterpretedOptionNamePart builder] mergeFromCodedInputStream:input] build];
+}
++ (PBUninterpretedOptionNamePart*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBUninterpretedOptionNamePart*)[[[PBUninterpretedOptionNamePart builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBUninterpretedOptionNamePartBuilder*) builder {
+  return [[PBUninterpretedOptionNamePartBuilder alloc] init];
+}
++ (PBUninterpretedOptionNamePartBuilder*) builderWithPrototype:(PBUninterpretedOptionNamePart*) prototype {
+  return [[PBUninterpretedOptionNamePart builder] mergeFrom:prototype];
+}
+- (PBUninterpretedOptionNamePartBuilder*) builder {
+  return [PBUninterpretedOptionNamePart builder];
+}
+- (PBUninterpretedOptionNamePartBuilder*) toBuilder {
+  return [PBUninterpretedOptionNamePart builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  if (self.hasNamePart) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"namePart", self.namePart];
+  }
+  if (self.hasIsExtension) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"isExtension", [NSNumber numberWithBool:self.isExtension]];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBUninterpretedOptionNamePart class]]) {
+    return NO;
+  }
+  PBUninterpretedOptionNamePart *otherMessage = other;
+  return
+      self.hasNamePart == otherMessage.hasNamePart &&
+      (!self.hasNamePart || [self.namePart isEqual:otherMessage.namePart]) &&
+      self.hasIsExtension == otherMessage.hasIsExtension &&
+      (!self.hasIsExtension || self.isExtension == otherMessage.isExtension) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  if (self.hasNamePart) {
+    hashCode = hashCode * 31 + [self.namePart hash];
+  }
+  if (self.hasIsExtension) {
+    hashCode = hashCode * 31 + [[NSNumber numberWithBool:self.isExtension] hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBUninterpretedOptionNamePartBuilder()
+@property (strong) PBUninterpretedOptionNamePart* result;
+@end
+
+@implementation PBUninterpretedOptionNamePartBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBUninterpretedOptionNamePart alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBUninterpretedOptionNamePartBuilder*) clear {
+  self.result = [[PBUninterpretedOptionNamePart alloc] init];
+  return self;
+}
+- (PBUninterpretedOptionNamePartBuilder*) clone {
+  return [PBUninterpretedOptionNamePart builderWithPrototype:result];
+}
+- (PBUninterpretedOptionNamePart*) defaultInstance {
+  return [PBUninterpretedOptionNamePart defaultInstance];
+}
+- (PBUninterpretedOptionNamePart*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBUninterpretedOptionNamePart*) buildPartial {
+  PBUninterpretedOptionNamePart* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBUninterpretedOptionNamePartBuilder*) mergeFrom:(PBUninterpretedOptionNamePart*) other {
+  if (other == [PBUninterpretedOptionNamePart defaultInstance]) {
+    return self;
+  }
+  if (other.hasNamePart) {
+    [self setNamePart:other.namePart];
+  }
+  if (other.hasIsExtension) {
+    [self setIsExtension:other.isExtension];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBUninterpretedOptionNamePartBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBUninterpretedOptionNamePartBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        [self setNamePart:[input readString]];
+        break;
+      }
+      case 16: {
+        [self setIsExtension:[input readBool]];
+        break;
+      }
+    }
+  }
+}
+- (BOOL) hasNamePart {
+  return result.hasNamePart;
+}
+- (NSString*) namePart {
+  return result.namePart;
+}
+- (PBUninterpretedOptionNamePartBuilder*) setNamePart:(NSString*) value {
+  result.hasNamePart = YES;
+  result.namePart = value;
+  return self;
+}
+- (PBUninterpretedOptionNamePartBuilder*) clearNamePart {
+  result.hasNamePart = NO;
+  result.namePart = @"";
+  return self;
+}
+- (BOOL) hasIsExtension {
+  return result.hasIsExtension;
+}
+- (BOOL) isExtension {
+  return result.isExtension;
+}
+- (PBUninterpretedOptionNamePartBuilder*) setIsExtension:(BOOL) value {
+  result.hasIsExtension = YES;
+  result.isExtension = value;
+  return self;
+}
+- (PBUninterpretedOptionNamePartBuilder*) clearIsExtension {
+  result.hasIsExtension = NO;
+  result.isExtension = NO;
+  return self;
+}
+@end
+
+@interface PBUninterpretedOptionBuilder()
+@property (strong) PBUninterpretedOption* result;
+@end
+
+@implementation PBUninterpretedOptionBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBUninterpretedOption alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBUninterpretedOptionBuilder*) clear {
+  self.result = [[PBUninterpretedOption alloc] init];
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) clone {
+  return [PBUninterpretedOption builderWithPrototype:result];
+}
+- (PBUninterpretedOption*) defaultInstance {
+  return [PBUninterpretedOption defaultInstance];
+}
+- (PBUninterpretedOption*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBUninterpretedOption*) buildPartial {
+  PBUninterpretedOption* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBUninterpretedOptionBuilder*) mergeFrom:(PBUninterpretedOption*) other {
+  if (other == [PBUninterpretedOption defaultInstance]) {
+    return self;
+  }
+  if (other.nameArray.count > 0) {
+    if (result.nameArray == nil) {
+      result.nameArray = [[NSMutableArray alloc] initWithArray:other.nameArray];
+    } else {
+      [result.nameArray addObjectsFromArray:other.nameArray];
+    }
+  }
+  if (other.hasIdentifierValue) {
+    [self setIdentifierValue:other.identifierValue];
+  }
+  if (other.hasPositiveIntValue) {
+    [self setPositiveIntValue:other.positiveIntValue];
+  }
+  if (other.hasNegativeIntValue) {
+    [self setNegativeIntValue:other.negativeIntValue];
+  }
+  if (other.hasDoubleValue) {
+    [self setDoubleValue:other.doubleValue];
+  }
+  if (other.hasStringValue) {
+    [self setStringValue:other.stringValue];
+  }
+  if (other.hasAggregateValue) {
+    [self setAggregateValue:other.aggregateValue];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBUninterpretedOptionBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 18: {
+        PBUninterpretedOptionNamePartBuilder* subBuilder = [PBUninterpretedOptionNamePart builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addName:[subBuilder buildPartial]];
+        break;
+      }
+      case 26: {
+        [self setIdentifierValue:[input readString]];
+        break;
+      }
+      case 32: {
+        [self setPositiveIntValue:[input readUInt64]];
+        break;
+      }
+      case 40: {
+        [self setNegativeIntValue:[input readInt64]];
+        break;
+      }
+      case 49: {
+        [self setDoubleValue:[input readDouble]];
+        break;
+      }
+      case 58: {
+        [self setStringValue:[input readData]];
+        break;
+      }
+      case 66: {
+        [self setAggregateValue:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (NSMutableArray *)name {
+  return result.nameArray;
+}
+- (PBUninterpretedOptionNamePart*)nameAtIndex:(NSUInteger)index {
+  return [result nameAtIndex:index];
+}
+- (PBUninterpretedOptionBuilder *)addName:(PBUninterpretedOptionNamePart*)value {
+  if (result.nameArray == nil) {
+    result.nameArray = [[NSMutableArray alloc]init];
+  }
+  [result.nameArray addObject:value];
+  return self;
+}
+- (PBUninterpretedOptionBuilder *)setNameArray:(NSArray *)array {
+  result.nameArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBUninterpretedOptionBuilder *)clearName {
+  result.nameArray = nil;
+  return self;
+}
+- (BOOL) hasIdentifierValue {
+  return result.hasIdentifierValue;
+}
+- (NSString*) identifierValue {
+  return result.identifierValue;
+}
+- (PBUninterpretedOptionBuilder*) setIdentifierValue:(NSString*) value {
+  result.hasIdentifierValue = YES;
+  result.identifierValue = value;
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) clearIdentifierValue {
+  result.hasIdentifierValue = NO;
+  result.identifierValue = @"";
+  return self;
+}
+- (BOOL) hasPositiveIntValue {
+  return result.hasPositiveIntValue;
+}
+- (UInt64) positiveIntValue {
+  return result.positiveIntValue;
+}
+- (PBUninterpretedOptionBuilder*) setPositiveIntValue:(UInt64) value {
+  result.hasPositiveIntValue = YES;
+  result.positiveIntValue = value;
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) clearPositiveIntValue {
+  result.hasPositiveIntValue = NO;
+  result.positiveIntValue = 0L;
+  return self;
+}
+- (BOOL) hasNegativeIntValue {
+  return result.hasNegativeIntValue;
+}
+- (SInt64) negativeIntValue {
+  return result.negativeIntValue;
+}
+- (PBUninterpretedOptionBuilder*) setNegativeIntValue:(SInt64) value {
+  result.hasNegativeIntValue = YES;
+  result.negativeIntValue = value;
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) clearNegativeIntValue {
+  result.hasNegativeIntValue = NO;
+  result.negativeIntValue = 0L;
+  return self;
+}
+- (BOOL) hasDoubleValue {
+  return result.hasDoubleValue;
+}
+- (Float64) doubleValue {
+  return result.doubleValue;
+}
+- (PBUninterpretedOptionBuilder*) setDoubleValue:(Float64) value {
+  result.hasDoubleValue = YES;
+  result.doubleValue = value;
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) clearDoubleValue {
+  result.hasDoubleValue = NO;
+  result.doubleValue = 0;
+  return self;
+}
+- (BOOL) hasStringValue {
+  return result.hasStringValue;
+}
+- (NSData*) stringValue {
+  return result.stringValue;
+}
+- (PBUninterpretedOptionBuilder*) setStringValue:(NSData*) value {
+  result.hasStringValue = YES;
+  result.stringValue = value;
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) clearStringValue {
+  result.hasStringValue = NO;
+  result.stringValue = [NSData data];
+  return self;
+}
+- (BOOL) hasAggregateValue {
+  return result.hasAggregateValue;
+}
+- (NSString*) aggregateValue {
+  return result.aggregateValue;
+}
+- (PBUninterpretedOptionBuilder*) setAggregateValue:(NSString*) value {
+  result.hasAggregateValue = YES;
+  result.aggregateValue = value;
+  return self;
+}
+- (PBUninterpretedOptionBuilder*) clearAggregateValue {
+  result.hasAggregateValue = NO;
+  result.aggregateValue = @"";
+  return self;
+}
+@end
+
+@interface PBSourceCodeInfo ()
+@property (strong) NSMutableArray * locationArray;
+@end
+
+@implementation PBSourceCodeInfo
+
+@synthesize locationArray;
+@dynamic location;
+- (id) init {
+  if ((self = [super init])) {
+  }
+  return self;
+}
+static PBSourceCodeInfo* defaultPBSourceCodeInfoInstance = nil;
++ (void) initialize {
+  if (self == [PBSourceCodeInfo class]) {
+    defaultPBSourceCodeInfoInstance = [[PBSourceCodeInfo alloc] init];
+  }
+}
++ (PBSourceCodeInfo*) defaultInstance {
+  return defaultPBSourceCodeInfoInstance;
+}
+- (PBSourceCodeInfo*) defaultInstance {
+  return defaultPBSourceCodeInfoInstance;
+}
+- (NSArray *)location {
+  return locationArray;
+}
+- (PBSourceCodeInfoLocation*)locationAtIndex:(NSUInteger)index {
+  return [locationArray objectAtIndex:index];
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  [self.locationArray enumerateObjectsUsingBlock:^(PBSourceCodeInfoLocation *element, NSUInteger idx, BOOL *stop) {
+    [output writeMessage:1 value:element];
+  }];
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  [self.locationArray enumerateObjectsUsingBlock:^(PBSourceCodeInfoLocation *element, NSUInteger idx, BOOL *stop) {
+    size_ += computeMessageSize(1, element);
+  }];
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBSourceCodeInfo*) parseFromData:(NSData*) data {
+  return (PBSourceCodeInfo*)[[[PBSourceCodeInfo builder] mergeFromData:data] build];
+}
++ (PBSourceCodeInfo*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBSourceCodeInfo*)[[[PBSourceCodeInfo builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBSourceCodeInfo*) parseFromInputStream:(NSInputStream*) input {
+  return (PBSourceCodeInfo*)[[[PBSourceCodeInfo builder] mergeFromInputStream:input] build];
+}
++ (PBSourceCodeInfo*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBSourceCodeInfo*)[[[PBSourceCodeInfo builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBSourceCodeInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBSourceCodeInfo*)[[[PBSourceCodeInfo builder] mergeFromCodedInputStream:input] build];
+}
++ (PBSourceCodeInfo*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBSourceCodeInfo*)[[[PBSourceCodeInfo builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBSourceCodeInfoBuilder*) builder {
+  return [[PBSourceCodeInfoBuilder alloc] init];
+}
++ (PBSourceCodeInfoBuilder*) builderWithPrototype:(PBSourceCodeInfo*) prototype {
+  return [[PBSourceCodeInfo builder] mergeFrom:prototype];
+}
+- (PBSourceCodeInfoBuilder*) builder {
+  return [PBSourceCodeInfo builder];
+}
+- (PBSourceCodeInfoBuilder*) toBuilder {
+  return [PBSourceCodeInfo builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.locationArray enumerateObjectsUsingBlock:^(PBSourceCodeInfoLocation *element, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@ {\n", indent, @"location"];
+    [element writeDescriptionTo:output
+                     withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+    [output appendFormat:@"%@}\n", indent];
+  }];
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBSourceCodeInfo class]]) {
+    return NO;
+  }
+  PBSourceCodeInfo *otherMessage = other;
+  return
+      [self.locationArray isEqualToArray:otherMessage.locationArray] &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  [self.locationArray enumerateObjectsUsingBlock:^(PBSourceCodeInfoLocation *element, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [element hash];
+  }];
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBSourceCodeInfoLocation ()
+@property (strong) PBAppendableArray * pathArray;
+@property (strong) PBAppendableArray * spanArray;
+@property (strong) NSString* leadingComments;
+@property (strong) NSString* trailingComments;
+@end
+
+@implementation PBSourceCodeInfoLocation
+
+@synthesize pathArray;
+@dynamic path;
+@synthesize spanArray;
+@dynamic span;
+- (BOOL) hasLeadingComments {
+  return !!hasLeadingComments_;
+}
+- (void) setHasLeadingComments:(BOOL) value_ {
+  hasLeadingComments_ = !!value_;
+}
+@synthesize leadingComments;
+- (BOOL) hasTrailingComments {
+  return !!hasTrailingComments_;
+}
+- (void) setHasTrailingComments:(BOOL) value_ {
+  hasTrailingComments_ = !!value_;
+}
+@synthesize trailingComments;
+- (id) init {
+  if ((self = [super init])) {
+    self.leadingComments = @"";
+    self.trailingComments = @"";
+  }
+  return self;
+}
+static PBSourceCodeInfoLocation* defaultPBSourceCodeInfoLocationInstance = nil;
++ (void) initialize {
+  if (self == [PBSourceCodeInfoLocation class]) {
+    defaultPBSourceCodeInfoLocationInstance = [[PBSourceCodeInfoLocation alloc] init];
+  }
+}
++ (PBSourceCodeInfoLocation*) defaultInstance {
+  return defaultPBSourceCodeInfoLocationInstance;
+}
+- (PBSourceCodeInfoLocation*) defaultInstance {
+  return defaultPBSourceCodeInfoLocationInstance;
+}
+- (PBArray *)path {
+  return pathArray;
+}
+- (SInt32)pathAtIndex:(NSUInteger)index {
+  return [pathArray int32AtIndex:index];
+}
+- (PBArray *)span {
+  return spanArray;
+}
+- (SInt32)spanAtIndex:(NSUInteger)index {
+  return [spanArray int32AtIndex:index];
+}
+- (BOOL) isInitialized {
+  return YES;
+}
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  const NSUInteger pathArrayCount = self.pathArray.count;
+  if (pathArrayCount > 0) {
+    const SInt32 *values = (const SInt32 *)self.pathArray.data;
+    [output writeRawVarint32:10];
+    [output writeRawVarint32:pathMemoizedSerializedSize];
+    for (NSUInteger i = 0; i < pathArrayCount; ++i) {
+      [output writeInt32NoTag:values[i]];
+    }
+  }
+  const NSUInteger spanArrayCount = self.spanArray.count;
+  if (spanArrayCount > 0) {
+    const SInt32 *values = (const SInt32 *)self.spanArray.data;
+    [output writeRawVarint32:18];
+    [output writeRawVarint32:spanMemoizedSerializedSize];
+    for (NSUInteger i = 0; i < spanArrayCount; ++i) {
+      [output writeInt32NoTag:values[i]];
+    }
+  }
+  if (self.hasLeadingComments) {
+    [output writeString:3 value:self.leadingComments];
+  }
+  if (self.hasTrailingComments) {
+    [output writeString:4 value:self.trailingComments];
+  }
+  [self.unknownFields writeToCodedOutputStream:output];
+}
+- (SInt32) serializedSize {
+  __block SInt32 size_ = memoizedSerializedSize;
+  if (size_ != -1) {
+    return size_;
+  }
+
+  size_ = 0;
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.pathArray.count;
+    const SInt32 *values = (const SInt32 *)self.pathArray.data;
+    for (NSUInteger i = 0; i < count; ++i) {
+      dataSize += computeInt32SizeNoTag(values[i]);
+    }
+    size_ += dataSize;
+    if (count > 0) {
+      size_ += 1;
+      size_ += computeInt32SizeNoTag(dataSize);
+    }
+    pathMemoizedSerializedSize = dataSize;
+  }
+  {
+    __block SInt32 dataSize = 0;
+    const NSUInteger count = self.spanArray.count;
+    const SInt32 *values = (const SInt32 *)self.spanArray.data;
+    for (NSUInteger i = 0; i < count; ++i) {
+      dataSize += computeInt32SizeNoTag(values[i]);
+    }
+    size_ += dataSize;
+    if (count > 0) {
+      size_ += 1;
+      size_ += computeInt32SizeNoTag(dataSize);
+    }
+    spanMemoizedSerializedSize = dataSize;
+  }
+  if (self.hasLeadingComments) {
+    size_ += computeStringSize(3, self.leadingComments);
+  }
+  if (self.hasTrailingComments) {
+    size_ += computeStringSize(4, self.trailingComments);
+  }
+  size_ += self.unknownFields.serializedSize;
+  memoizedSerializedSize = size_;
+  return size_;
+}
++ (PBSourceCodeInfoLocation*) parseFromData:(NSData*) data {
+  return (PBSourceCodeInfoLocation*)[[[PBSourceCodeInfoLocation builder] mergeFromData:data] build];
+}
++ (PBSourceCodeInfoLocation*) parseFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBSourceCodeInfoLocation*)[[[PBSourceCodeInfoLocation builder] mergeFromData:data extensionRegistry:extensionRegistry] build];
+}
++ (PBSourceCodeInfoLocation*) parseFromInputStream:(NSInputStream*) input {
+  return (PBSourceCodeInfoLocation*)[[[PBSourceCodeInfoLocation builder] mergeFromInputStream:input] build];
+}
++ (PBSourceCodeInfoLocation*) parseFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBSourceCodeInfoLocation*)[[[PBSourceCodeInfoLocation builder] mergeFromInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBSourceCodeInfoLocation*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return (PBSourceCodeInfoLocation*)[[[PBSourceCodeInfoLocation builder] mergeFromCodedInputStream:input] build];
+}
++ (PBSourceCodeInfoLocation*) parseFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  return (PBSourceCodeInfoLocation*)[[[PBSourceCodeInfoLocation builder] mergeFromCodedInputStream:input extensionRegistry:extensionRegistry] build];
+}
++ (PBSourceCodeInfoLocationBuilder*) builder {
+  return [[PBSourceCodeInfoLocationBuilder alloc] init];
+}
++ (PBSourceCodeInfoLocationBuilder*) builderWithPrototype:(PBSourceCodeInfoLocation*) prototype {
+  return [[PBSourceCodeInfoLocation builder] mergeFrom:prototype];
+}
+- (PBSourceCodeInfoLocationBuilder*) builder {
+  return [PBSourceCodeInfoLocation builder];
+}
+- (PBSourceCodeInfoLocationBuilder*) toBuilder {
+  return [PBSourceCodeInfoLocation builderWithPrototype:self];
+}
+- (void) writeDescriptionTo:(NSMutableString*) output withIndent:(NSString*) indent {
+  [self.pathArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"path", obj];
+  }];
+  [self.spanArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"span", obj];
+  }];
+  if (self.hasLeadingComments) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"leadingComments", self.leadingComments];
+  }
+  if (self.hasTrailingComments) {
+    [output appendFormat:@"%@%@: %@\n", indent, @"trailingComments", self.trailingComments];
+  }
+  [self.unknownFields writeDescriptionTo:output withIndent:indent];
+}
+- (BOOL) isEqual:(id)other {
+  if (other == self) {
+    return YES;
+  }
+  if (![other isKindOfClass:[PBSourceCodeInfoLocation class]]) {
+    return NO;
+  }
+  PBSourceCodeInfoLocation *otherMessage = other;
+  return
+      [self.pathArray isEqualToArray:otherMessage.pathArray] &&
+      [self.spanArray isEqualToArray:otherMessage.spanArray] &&
+      self.hasLeadingComments == otherMessage.hasLeadingComments &&
+      (!self.hasLeadingComments || [self.leadingComments isEqual:otherMessage.leadingComments]) &&
+      self.hasTrailingComments == otherMessage.hasTrailingComments &&
+      (!self.hasTrailingComments || [self.trailingComments isEqual:otherMessage.trailingComments]) &&
+      (self.unknownFields == otherMessage.unknownFields || (self.unknownFields != nil && [self.unknownFields isEqual:otherMessage.unknownFields]));
+}
+- (NSUInteger) hash {
+  __block NSUInteger hashCode = 7;
+  [self.pathArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [obj longValue];
+  }];
+  [self.spanArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+    hashCode = hashCode * 31 + [obj longValue];
+  }];
+  if (self.hasLeadingComments) {
+    hashCode = hashCode * 31 + [self.leadingComments hash];
+  }
+  if (self.hasTrailingComments) {
+    hashCode = hashCode * 31 + [self.trailingComments hash];
+  }
+  hashCode = hashCode * 31 + [self.unknownFields hash];
+  return hashCode;
+}
+@end
+
+@interface PBSourceCodeInfoLocationBuilder()
+@property (strong) PBSourceCodeInfoLocation* result;
+@end
+
+@implementation PBSourceCodeInfoLocationBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBSourceCodeInfoLocation alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBSourceCodeInfoLocationBuilder*) clear {
+  self.result = [[PBSourceCodeInfoLocation alloc] init];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder*) clone {
+  return [PBSourceCodeInfoLocation builderWithPrototype:result];
+}
+- (PBSourceCodeInfoLocation*) defaultInstance {
+  return [PBSourceCodeInfoLocation defaultInstance];
+}
+- (PBSourceCodeInfoLocation*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBSourceCodeInfoLocation*) buildPartial {
+  PBSourceCodeInfoLocation* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBSourceCodeInfoLocationBuilder*) mergeFrom:(PBSourceCodeInfoLocation*) other {
+  if (other == [PBSourceCodeInfoLocation defaultInstance]) {
+    return self;
+  }
+  if (other.pathArray.count > 0) {
+    if (result.pathArray == nil) {
+      result.pathArray = [other.pathArray copy];
+    } else {
+      [result.pathArray appendArray:other.pathArray];
+    }
+  }
+  if (other.spanArray.count > 0) {
+    if (result.spanArray == nil) {
+      result.spanArray = [other.spanArray copy];
+    } else {
+      [result.spanArray appendArray:other.spanArray];
+    }
+  }
+  if (other.hasLeadingComments) {
+    [self setLeadingComments:other.leadingComments];
+  }
+  if (other.hasTrailingComments) {
+    [self setTrailingComments:other.trailingComments];
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBSourceCodeInfoLocationBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        SInt32 length = [input readRawVarint32];
+        SInt32 limit = [input pushLimit:length];
+        if (result.pathArray == nil) {
+          result.pathArray = [PBAppendableArray arrayWithValueType:PBArrayValueTypeInt32];
+        }
+        while (input.bytesUntilLimit > 0) {
+          [result.pathArray addInt32:[input readInt32]];
+        }
+        [input popLimit:limit];
+        break;
+      }
+      case 18: {
+        SInt32 length = [input readRawVarint32];
+        SInt32 limit = [input pushLimit:length];
+        if (result.spanArray == nil) {
+          result.spanArray = [PBAppendableArray arrayWithValueType:PBArrayValueTypeInt32];
+        }
+        while (input.bytesUntilLimit > 0) {
+          [result.spanArray addInt32:[input readInt32]];
+        }
+        [input popLimit:limit];
+        break;
+      }
+      case 26: {
+        [self setLeadingComments:[input readString]];
+        break;
+      }
+      case 34: {
+        [self setTrailingComments:[input readString]];
+        break;
+      }
+    }
+  }
+}
+- (PBAppendableArray *)path {
+  return result.pathArray;
+}
+- (SInt32)pathAtIndex:(NSUInteger)index {
+  return [result pathAtIndex:index];
+}
+- (PBSourceCodeInfoLocationBuilder *)addPath:(SInt32)value {
+  if (result.pathArray == nil) {
+    result.pathArray = [PBAppendableArray arrayWithValueType:PBArrayValueTypeInt32];
+  }
+  [result.pathArray addInt32:value];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder *)setPathArray:(NSArray *)array {
+  result.pathArray = [PBAppendableArray arrayWithArray:array valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder *)setPathValues:(const SInt32 *)values count:(NSUInteger)count {
+  result.pathArray = [PBAppendableArray arrayWithValues:values count:count valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder *)clearPath {
+  result.pathArray = nil;
+  return self;
+}
+- (PBAppendableArray *)span {
+  return result.spanArray;
+}
+- (SInt32)spanAtIndex:(NSUInteger)index {
+  return [result spanAtIndex:index];
+}
+- (PBSourceCodeInfoLocationBuilder *)addSpan:(SInt32)value {
+  if (result.spanArray == nil) {
+    result.spanArray = [PBAppendableArray arrayWithValueType:PBArrayValueTypeInt32];
+  }
+  [result.spanArray addInt32:value];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder *)setSpanArray:(NSArray *)array {
+  result.spanArray = [PBAppendableArray arrayWithArray:array valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder *)setSpanValues:(const SInt32 *)values count:(NSUInteger)count {
+  result.spanArray = [PBAppendableArray arrayWithValues:values count:count valueType:PBArrayValueTypeInt32];
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder *)clearSpan {
+  result.spanArray = nil;
+  return self;
+}
+- (BOOL) hasLeadingComments {
+  return result.hasLeadingComments;
+}
+- (NSString*) leadingComments {
+  return result.leadingComments;
+}
+- (PBSourceCodeInfoLocationBuilder*) setLeadingComments:(NSString*) value {
+  result.hasLeadingComments = YES;
+  result.leadingComments = value;
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder*) clearLeadingComments {
+  result.hasLeadingComments = NO;
+  result.leadingComments = @"";
+  return self;
+}
+- (BOOL) hasTrailingComments {
+  return result.hasTrailingComments;
+}
+- (NSString*) trailingComments {
+  return result.trailingComments;
+}
+- (PBSourceCodeInfoLocationBuilder*) setTrailingComments:(NSString*) value {
+  result.hasTrailingComments = YES;
+  result.trailingComments = value;
+  return self;
+}
+- (PBSourceCodeInfoLocationBuilder*) clearTrailingComments {
+  result.hasTrailingComments = NO;
+  result.trailingComments = @"";
+  return self;
+}
+@end
+
+@interface PBSourceCodeInfoBuilder()
+@property (strong) PBSourceCodeInfo* result;
+@end
+
+@implementation PBSourceCodeInfoBuilder
+@synthesize result;
+- (id) init {
+  if ((self = [super init])) {
+    self.result = [[PBSourceCodeInfo alloc] init];
+  }
+  return self;
+}
+- (PBGeneratedMessage*) internalGetResult {
+  return result;
+}
+- (PBSourceCodeInfoBuilder*) clear {
+  self.result = [[PBSourceCodeInfo alloc] init];
+  return self;
+}
+- (PBSourceCodeInfoBuilder*) clone {
+  return [PBSourceCodeInfo builderWithPrototype:result];
+}
+- (PBSourceCodeInfo*) defaultInstance {
+  return [PBSourceCodeInfo defaultInstance];
+}
+- (PBSourceCodeInfo*) build {
+  [self checkInitialized];
+  return [self buildPartial];
+}
+- (PBSourceCodeInfo*) buildPartial {
+  PBSourceCodeInfo* returnMe = result;
+  self.result = nil;
+  return returnMe;
+}
+- (PBSourceCodeInfoBuilder*) mergeFrom:(PBSourceCodeInfo*) other {
+  if (other == [PBSourceCodeInfo defaultInstance]) {
+    return self;
+  }
+  if (other.locationArray.count > 0) {
+    if (result.locationArray == nil) {
+      result.locationArray = [[NSMutableArray alloc] initWithArray:other.locationArray];
+    } else {
+      [result.locationArray addObjectsFromArray:other.locationArray];
+    }
+  }
+  [self mergeUnknownFields:other.unknownFields];
+  return self;
+}
+- (PBSourceCodeInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  return [self mergeFromCodedInputStream:input extensionRegistry:[PBExtensionRegistry emptyRegistry]];
+}
+- (PBSourceCodeInfoBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBUnknownFieldSetBuilder* unknownFields = [PBUnknownFieldSet builderWithUnknownFields:self.unknownFields];
+  while (YES) {
+    SInt32 tag = [input readTag];
+    switch (tag) {
+      case 0:
+        [self setUnknownFields:[unknownFields build]];
+        return self;
+      default: {
+        if (![self parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag]) {
+          [self setUnknownFields:[unknownFields build]];
+          return self;
+        }
+        break;
+      }
+      case 10: {
+        PBSourceCodeInfoLocationBuilder* subBuilder = [PBSourceCodeInfoLocation builder];
+        [input readMessage:subBuilder extensionRegistry:extensionRegistry];
+        [self addLocation:[subBuilder buildPartial]];
+        break;
+      }
+    }
+  }
+}
+- (NSMutableArray *)location {
+  return result.locationArray;
+}
+- (PBSourceCodeInfoLocation*)locationAtIndex:(NSUInteger)index {
+  return [result locationAtIndex:index];
+}
+- (PBSourceCodeInfoBuilder *)addLocation:(PBSourceCodeInfoLocation*)value {
+  if (result.locationArray == nil) {
+    result.locationArray = [[NSMutableArray alloc]init];
+  }
+  [result.locationArray addObject:value];
+  return self;
+}
+- (PBSourceCodeInfoBuilder *)setLocationArray:(NSArray *)array {
+  result.locationArray = [[NSMutableArray alloc]initWithArray:array];
+  return self;
+}
+- (PBSourceCodeInfoBuilder *)clearLocation {
+  result.locationArray = nil;
+  return self;
+}
+@end
+
+
+// @@protoc_insertion_point(global_scope)
diff --git a/src/runtime/Classes/ExtendableMessage.h b/src/runtime/Classes/ExtendableMessage.h
new file mode 100755
index 0000000..43c3eb7
--- /dev/null
+++ b/src/runtime/Classes/ExtendableMessage.h
@@ -0,0 +1,90 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "GeneratedMessage.h"
+
+#import "ExtensionField.h"
+
+/**
+ * Generated message classes for message types that contain extension ranges
+ * subclass this.
+ *
+ * <p>This class implements type-safe accessors for extensions.  They
+ * implement all the same operations that you can do with normal fields --
+ * e.g. "has", "get", and "getCount" -- but for extensions.  The extensions
+ * are identified using instances of the class {@link GeneratedExtension};
+ * the protocol compiler generates a static instance of this class for every
+ * extension in its input.  Through the magic of generics, all is made
+ * type-safe.
+ *
+ * <p>For example, imagine you have the {@code .proto} file:
+ *
+ * <pre>
+ * option java_class = "MyProto";
+ *
+ * message Foo {
+ *   extensions 1000 to max;
+ * }
+ *
+ * extend Foo {
+ *   optional int32 bar;
+ * }
+ * </pre>
+ *
+ * <p>Then you might write code like:
+ *
+ * <pre>
+ * MyProto.Foo foo = getFoo();
+ * int i = foo.getExtension(MyProto.bar);
+ * </pre>
+ *
+ * <p>See also {@link ExtendableBuilder}.
+ */
+@interface PBExtendableMessage : PBGeneratedMessage {
+@private
+  NSMutableDictionary* extensionMap;
+  NSMutableDictionary* extensionRegistry;
+}
+
+@property (strong) NSMutableDictionary* extensionMap;
+@property (strong) NSMutableDictionary* extensionRegistry;
+
+- (BOOL) hasExtension:(id<PBExtensionField>) extension;
+- (id) getExtension:(id<PBExtensionField>) extension;
+
+//@protected
+- (BOOL) extensionsAreInitialized;
+- (SInt32) extensionsSerializedSize;
+- (void) writeExtensionsToCodedOutputStream:(PBCodedOutputStream*) output
+                                       from:(SInt32) startInclusive
+                                         to:(SInt32) endExclusive;
+- (void) writeExtensionDescriptionToMutableString:(NSMutableString*) output
+                                             from:(SInt32) startInclusive
+                                               to:(SInt32) endExclusive
+                                       withIndent:(NSString*) indent;
+- (BOOL) isEqualExtensionsInOther:(PBExtendableMessage*)otherMessage
+                             from:(SInt32) startInclusive
+                               to:(SInt32) endExclusive;
+- (NSUInteger) hashExtensionsFrom:(SInt32) startInclusive
+                               to:(SInt32) endExclusive;
+
+
+
+/* @internal */
+- (void) ensureExtensionIsRegistered:(id<PBExtensionField>) extension;
+
+@end
diff --git a/src/runtime/Classes/ExtendableMessage.m b/src/runtime/Classes/ExtendableMessage.m
new file mode 100755
index 0000000..5495637
--- /dev/null
+++ b/src/runtime/Classes/ExtendableMessage.m
@@ -0,0 +1,155 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "ExtendableMessage.h"
+
+#import "ExtensionField.h"
+
+@implementation PBExtendableMessage
+
+@synthesize extensionMap;
+@synthesize extensionRegistry;
+
+
+
+
+- (BOOL) isInitialized:(id) object {
+  if ([object isKindOfClass:[NSArray class]]) {
+    for (id child in object) {
+      if (![self isInitialized:child]) {
+        return NO;
+      }
+    }
+  } else if ([object conformsToProtocol:@protocol(PBMessage)]) {
+    return [object isInitialized];
+  }
+
+  return YES;
+}
+
+
+- (BOOL) extensionsAreInitialized {
+  return [self isInitialized:extensionMap.allValues];
+}
+
+
+- (id) getExtension:(id<PBExtensionField>) extension {
+  [self ensureExtensionIsRegistered:extension];
+  id value = [extensionMap objectForKey:@([extension fieldNumber])];
+  if (value != nil) {
+    return value;
+  }
+
+  return [extension defaultValue];
+}
+
+
+- (void) ensureExtensionIsRegistered:(id<PBExtensionField>) extension {
+  if ([extension extendedClass] != [self class]) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Trying to use an extension for another type" userInfo:nil];
+  }
+
+  if (extensionRegistry == nil) {
+    self.extensionRegistry = [NSMutableDictionary dictionary];
+  }
+  [extensionRegistry setObject:extension
+                        forKey:@([extension fieldNumber])];
+}
+
+
+- (BOOL) hasExtension:(id<PBExtensionField>) extension {
+  return nil != [extensionMap objectForKey:@([extension fieldNumber])];
+}
+
+
+- (void) writeExtensionsToCodedOutputStream:(PBCodedOutputStream*) output
+                                       from:(SInt32) startInclusive
+                                         to:(SInt32) endExclusive {
+  // man, i really wish Cocoa had a Sorted/TreeMap
+  NSArray* sortedKeys = [extensionMap.allKeys sortedArrayUsingSelector:@selector(compare:)];
+  for (NSNumber* number in sortedKeys) {
+    SInt32 fieldNumber = (SInt32)[number integerValue];
+    if (fieldNumber >= startInclusive && fieldNumber < endExclusive) {
+      id<PBExtensionField> extension = [extensionRegistry objectForKey:number];
+      id value = [extensionMap objectForKey:number];
+      [extension writeValue:value includingTagToCodedOutputStream:output];
+    }
+  }
+}
+
+
+- (void) writeExtensionDescriptionToMutableString:(NSMutableString*) output
+                                             from:(SInt32) startInclusive
+                                               to:(SInt32) endExclusive
+                                       withIndent:(NSString*) indent {
+  NSArray* sortedKeys = [extensionMap.allKeys sortedArrayUsingSelector:@selector(compare:)];
+  for (NSNumber* number in sortedKeys) {
+    SInt32 fieldNumber = (SInt32)[number integerValue];
+    if (fieldNumber >= startInclusive && fieldNumber < endExclusive) {
+      id<PBExtensionField> extension = [extensionRegistry objectForKey:number];
+      id value = [extensionMap objectForKey:number];
+      [extension writeDescriptionOf:value to:output withIndent:indent];
+    }
+  }  
+}
+
+
+- (BOOL) isEqualExtensionsInOther:(PBExtendableMessage*)otherMessage
+                             from:(SInt32) startInclusive
+                               to:(SInt32) endExclusive {
+  NSArray* sortedKeys = [extensionMap.allKeys sortedArrayUsingSelector:@selector(compare:)];
+  for (NSNumber* number in sortedKeys) {
+    SInt32 fieldNumber = (SInt32)[number integerValue];
+    if (fieldNumber >= startInclusive && fieldNumber < endExclusive) {
+      id value = [extensionMap objectForKey:number];
+      id otherValue = [otherMessage.extensionMap objectForKey:number];
+      if (![value isEqual:otherValue]) {
+        return NO;
+      }
+    }
+  }
+  return YES;
+}
+
+
+- (NSUInteger) hashExtensionsFrom:(SInt32) startInclusive
+                               to:(SInt32) endExclusive {
+  NSUInteger hashCode = 0;
+  NSArray* sortedKeys = [extensionMap.allKeys sortedArrayUsingSelector:@selector(compare:)];
+  for (NSNumber* number in sortedKeys) {
+    SInt32 fieldNumber = (SInt32)[number integerValue];
+    if (fieldNumber >= startInclusive && fieldNumber < endExclusive) {
+      id value = [extensionMap objectForKey:number];
+      hashCode = hashCode * 31 + (NSUInteger)[value hash];
+    }
+  }
+  return hashCode;
+}
+
+
+- (SInt32) extensionsSerializedSize {
+  SInt32 size = 0;
+  for (NSNumber* number in extensionMap) {
+    id<PBExtensionField> extension = [extensionRegistry objectForKey:number];
+    id value = [extensionMap objectForKey:number];
+    size += [extension computeSerializedSizeIncludingTag:value];
+  }
+
+  return size;
+}
+
+@end
diff --git a/src/runtime/Classes/ExtendableMessageBuilder.h b/src/runtime/Classes/ExtendableMessageBuilder.h
new file mode 100755
index 0000000..764629b
--- /dev/null
+++ b/src/runtime/Classes/ExtendableMessageBuilder.h
@@ -0,0 +1,78 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "GeneratedMessageBuilder.h"
+
+#import "ExtensionField.h"
+
+@class PBExtendableMessage;
+
+/**
+ * Generated message builders for message types that contain extension ranges
+ * subclass this.
+ *
+ * <p>This class implements type-safe accessors for extensions.  They
+ * implement all the same operations that you can do with normal fields --
+ * e.g. "get", "set", and "add" -- but for extensions.  The extensions are
+ * identified using instances of the class {@link GeneratedExtension}; the
+ * protocol compiler generates a static instance of this class for every
+ * extension in its input.  Through the magic of generics, all is made
+ * type-safe.
+ *
+ * <p>For example, imagine you have the {@code .proto} file:
+ *
+ * <pre>
+ * option java_class = "MyProto";
+ *
+ * message Foo {
+ *   extensions 1000 to max;
+ * }
+ *
+ * extend Foo {
+ *   optional int32 bar;
+ * }
+ * </pre>
+ *
+ * <p>Then you might write code like:
+ *
+ * <pre>
+ * MyProto.Foo foo =
+ *   MyProto.Foo.newBuilder()
+ *     .setExtension(MyProto.bar, 123)
+ *     .build();
+ * </pre>
+ *
+ * <p>See also {@link ExtendableMessage}.
+ */
+@interface PBExtendableMessageBuilder : PBGeneratedMessageBuilder {
+}
+
+- (id) getExtension:(id<PBExtensionField>) extension;
+- (BOOL) hasExtension:(id<PBExtensionField>) extension;
+- (PBExtendableMessageBuilder*) setExtension:(id<PBExtensionField>) extension
+                                        value:(id) value;
+- (PBExtendableMessageBuilder*) addExtension:(id<PBExtensionField>) extension
+                                        value:(id) value;
+- (PBExtendableMessageBuilder*) setExtension:(id<PBExtensionField>) extension
+                                        index:(SInt32) index
+                                        value:(id) value;
+- (PBExtendableMessageBuilder*) clearExtension:(id<PBExtensionField>) extension;
+
+/* @protected */
+- (void) mergeExtensionFields:(PBExtendableMessage*) other;
+
+@end
diff --git a/src/runtime/Classes/ExtendableMessageBuilder.m b/src/runtime/Classes/ExtendableMessageBuilder.m
new file mode 100755
index 0000000..5a56b04
--- /dev/null
+++ b/src/runtime/Classes/ExtendableMessageBuilder.m
@@ -0,0 +1,175 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "ExtendableMessageBuilder.h"
+
+#import "ExtendableMessage.h"
+#import "ExtensionRegistry.h"
+#import "WireFormat.h"
+
+@implementation PBExtendableMessageBuilder
+
+- (PBExtendableMessage*) internalGetResult {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+/**
+ * Called by subclasses to parse an unknown field or an extension.
+ * @return {@code YES} unless the tag is an end-group tag.
+ */
+- (BOOL) parseUnknownField:(PBCodedInputStream*) input
+             unknownFields:(PBUnknownFieldSetBuilder*) unknownFields
+         extensionRegistry:(PBExtensionRegistry*) extensionRegistry
+                       tag:(SInt32) tag {
+  PBExtendableMessage* message = [self internalGetResult];
+  SInt32 wireType = PBWireFormatGetTagWireType(tag);
+  SInt32 fieldNumber = PBWireFormatGetTagFieldNumber(tag);
+
+  id<PBExtensionField> extension = [extensionRegistry getExtension:[message class]
+                                                       fieldNumber:fieldNumber];
+
+  if (extension != nil) {
+    if ([extension wireType] == wireType) {
+      [extension mergeFromCodedInputStream:input
+                             unknownFields:unknownFields
+                         extensionRegistry:extensionRegistry
+                                   builder:self
+                                       tag:tag];
+      return YES;
+    }
+  }
+
+  return [super parseUnknownField:input unknownFields:unknownFields extensionRegistry:extensionRegistry tag:tag];
+}
+
+
+- (id) getExtension:(id<PBExtensionField>) extension {
+  return [[self internalGetResult] getExtension:extension];
+}
+
+
+- (BOOL) hasExtension:(id<PBExtensionField>) extension {
+  return [[self internalGetResult] hasExtension:extension];
+}
+
+
+- (PBExtendableMessageBuilder*) setExtension:(id<PBExtensionField>) extension
+                                        value:(id) value {
+  PBExtendableMessage* message = [self internalGetResult];
+  [message ensureExtensionIsRegistered:extension];
+
+  if ([extension isRepeated]) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Must call addExtension() for repeated types." userInfo:nil];
+  }
+
+  if (message.extensionMap == nil) {
+    message.extensionMap = [NSMutableDictionary dictionary];
+  }
+  [message.extensionMap setObject:value forKey:@([extension fieldNumber])];
+  return self;
+}
+
+
+- (PBExtendableMessageBuilder*) addExtension:(id<PBExtensionField>) extension
+                                        value:(id) value {
+  PBExtendableMessage* message = [self internalGetResult];
+  [message ensureExtensionIsRegistered:extension];
+
+  if (![extension isRepeated]) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Must call setExtension() for singular types." userInfo:nil];
+  }
+
+  if (message.extensionMap == nil) {
+    message.extensionMap = [NSMutableDictionary dictionary];
+  }
+  NSNumber* fieldNumber = @([extension fieldNumber]);
+  NSMutableArray* list = [message.extensionMap objectForKey:fieldNumber];
+  if (list == nil) {
+    list = [NSMutableArray array];
+    [message.extensionMap setObject:list forKey:fieldNumber];
+  }
+
+  [list addObject:value];
+  return self;
+}
+
+
+- (PBExtendableMessageBuilder*) setExtension:(id<PBExtensionField>) extension
+                                        index:(SInt32) index
+                                        value:(id) value {
+  PBExtendableMessage* message = [self internalGetResult];
+  [message ensureExtensionIsRegistered:extension];
+
+  if (![extension isRepeated]) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Must call setExtension() for singular types." userInfo:nil];
+  }
+
+  if (message.extensionMap == nil) {
+    message.extensionMap = [NSMutableDictionary dictionary];
+  }
+
+  NSNumber* fieldNumber = @([extension fieldNumber]);
+  NSMutableArray* list = [message.extensionMap objectForKey:fieldNumber];
+
+  [list replaceObjectAtIndex:index withObject:value];
+
+  return self;
+}
+
+
+- (PBExtendableMessageBuilder*) clearExtension:(id<PBExtensionField>) extension {
+  PBExtendableMessage* message = [self internalGetResult];
+  [message ensureExtensionIsRegistered:extension];
+  [message.extensionMap removeObjectForKey:@([extension fieldNumber])];
+
+  return self;
+}
+
+
+- (void) mergeExtensionFields:(PBExtendableMessage*) other {
+  PBExtendableMessage* thisMessage = [self internalGetResult];
+  if ([thisMessage class] != [other class]) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Cannot merge extensions from a different type" userInfo:nil];
+  }
+
+  if (other.extensionMap.count > 0) {
+    if (thisMessage.extensionMap == nil) {
+      thisMessage.extensionMap = [NSMutableDictionary dictionary];
+    }
+
+    NSDictionary* registry = other.extensionRegistry;
+    for (NSNumber* fieldNumber in other.extensionMap) {
+      id<PBExtensionField> thisField = [registry objectForKey:fieldNumber];
+      id value = [other.extensionMap objectForKey:fieldNumber];
+
+      if ([thisField isRepeated]) {
+        NSMutableArray* list = [thisMessage.extensionMap objectForKey:fieldNumber];
+        if (list == nil) {
+          list = [NSMutableArray array];
+          [thisMessage.extensionMap setObject:list forKey:fieldNumber];
+        }
+
+        [list addObjectsFromArray:value];
+      } else {
+        [thisMessage.extensionMap setObject:value forKey:fieldNumber];
+      }
+    }
+  }
+}
+
+@end
diff --git a/src/runtime/Classes/ExtensionField.h b/src/runtime/Classes/ExtensionField.h
new file mode 100755
index 0000000..29f7a4f
--- /dev/null
+++ b/src/runtime/Classes/ExtensionField.h
@@ -0,0 +1,43 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "WireFormat.h"
+
+@class PBCodedInputStream;
+@class PBCodedOutputStream;
+@class PBExtendableMessageBuilder;
+@class PBExtensionRegistry;
+@class PBUnknownFieldSetBuilder;
+
+@protocol PBExtensionField
+- (SInt32) fieldNumber;
+- (PBWireFormat) wireType;
+- (BOOL) isRepeated;
+- (Class) extendedClass;
+- (id) defaultValue;
+
+- (void) mergeFromCodedInputStream:(PBCodedInputStream*) input
+                     unknownFields:(PBUnknownFieldSetBuilder*) unknownFields
+                 extensionRegistry:(PBExtensionRegistry*) extensionRegistry
+                           builder:(PBExtendableMessageBuilder*) builder
+                               tag:(SInt32) tag;
+- (void) writeValue:(id) value includingTagToCodedOutputStream:(PBCodedOutputStream*) output;
+- (SInt32) computeSerializedSizeIncludingTag:(id) value;
+- (void) writeDescriptionOf:(id) value
+                         to:(NSMutableString*) output
+                 withIndent:(NSString*) indent;
+@end
diff --git a/src/runtime/Classes/ExtensionRegistry.h b/src/runtime/Classes/ExtensionRegistry.h
new file mode 100755
index 0000000..733730e
--- /dev/null
+++ b/src/runtime/Classes/ExtensionRegistry.h
@@ -0,0 +1,86 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+/**
+ * A table of known extensions, searchable by name or field number.  When
+ * parsing a protocol message that might have extensions, you must provide
+ * an {@code ExtensionRegistry} in which you have registered any extensions
+ * that you want to be able to parse.  Otherwise, those extensions will just
+ * be treated like unknown fields.
+ *
+ * <p>For example, if you had the {@code .proto} file:
+ *
+ * <pre>
+ * option java_class = "MyProto";
+ *
+ * message Foo {
+ *   extensions 1000 to max;
+ * }
+ *
+ * extend Foo {
+ *   optional int32 bar;
+ * }
+ * </pre>
+ *
+ * Then you might write code like:
+ *
+ * <pre>
+ * ExtensionRegistry registry = ExtensionRegistry.newInstance();
+ * registry.add(MyProto.bar);
+ * MyProto.Foo message = MyProto.Foo.parseFrom(input, registry);
+ * </pre>
+ *
+ * <p>Background:
+ *
+ * <p>You might wonder why this is necessary.  Two alternatives might come to
+ * mind.  First, you might imagine a system where generated extensions are
+ * automatically registered when their containing classes are loaded.  This
+ * is a popular technique, but is bad design; among other things, it creates a
+ * situation where behavior can change depending on what classes happen to be
+ * loaded.  It also introduces a security vulnerability, because an
+ * unprivileged class could cause its code to be called unexpectedly from a
+ * privileged class by registering itself as an extension of the right type.
+ *
+ * <p>Another option you might consider is lazy parsing: do not parse an
+ * extension until it is first requested, at which point the caller must
+ * provide a type to use.  This introduces a different set of problems.  First,
+ * it would require a mutex lock any time an extension was accessed, which
+ * would be slow.  Second, corrupt data would not be detected until first
+ * access, at which point it would be much harder to deal with it.  Third, it
+ * could violate the expectation that message objects are immutable, since the
+ * type provided could be any arbitrary message class.  An unpriviledged user
+ * could take advantage of this to inject a mutable object into a message
+ * belonging to priviledged code and create mischief.
+ *
+ * @author Cyrus Najmabadi
+ */
+
+#import "ExtensionField.h"
+
+@interface PBExtensionRegistry : NSObject {
+@protected
+  NSDictionary* classMap;
+}
+
++ (PBExtensionRegistry*) emptyRegistry;
+- (id<PBExtensionField>) getExtension:(Class) clazz fieldNumber:(SInt32) fieldNumber;
+
+/* @protected */
+- (id) initWithClassMap:(NSDictionary*) classMap;
+- (id) keyForClass:(Class) clazz;
+
+@end
diff --git a/src/runtime/Classes/ExtensionRegistry.m b/src/runtime/Classes/ExtensionRegistry.m
new file mode 100755
index 0000000..4252888
--- /dev/null
+++ b/src/runtime/Classes/ExtensionRegistry.m
@@ -0,0 +1,62 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "ExtensionRegistry.h"
+
+@interface PBExtensionRegistry()
+@property (strong) NSDictionary* classMap;
+@end
+
+@implementation PBExtensionRegistry
+
+@synthesize classMap;
+
+
+static PBExtensionRegistry* emptyRegistry = nil;
+
++ (void) initialize {
+  if (self == [PBExtensionRegistry class]) {
+    emptyRegistry = [[PBExtensionRegistry alloc] initWithClassMap:[NSDictionary dictionary]];
+  }
+}
+
+
+- (id) initWithClassMap:(NSDictionary*) map_{
+  if ((self = [super init])) {
+    self.classMap = map_;
+  }
+
+  return self;
+}
+
+
+- (id) keyForClass:(Class) clazz {
+  return NSStringFromClass(clazz);
+}
+
+
++ (PBExtensionRegistry*) emptyRegistry {
+  return emptyRegistry;
+}
+
+
+- (id<PBExtensionField>) getExtension:(Class) clazz fieldNumber:(SInt32) fieldNumber {
+  NSDictionary* extensionMap = [classMap objectForKey:[self keyForClass:clazz]];
+  return [extensionMap objectForKey:[NSNumber numberWithInteger:fieldNumber]];
+}
+
+@end
diff --git a/src/runtime/Classes/Field.h b/src/runtime/Classes/Field.h
new file mode 100755
index 0000000..8c794bc
--- /dev/null
+++ b/src/runtime/Classes/Field.h
@@ -0,0 +1,50 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import <Foundation/Foundation.h>
+
+@class PBArray;
+@class PBAppendableArray;
+@class PBCodedOutputStream;
+
+@interface PBField : NSObject
+{
+@protected
+	PBAppendableArray *	_varintArray;
+	PBAppendableArray *	_fixed32Array;
+	PBAppendableArray *	_fixed64Array;
+	NSMutableArray *	_lengthDelimitedArray;
+	NSMutableArray *	_groupArray;
+}
+
+@property (nonatomic,strong,readonly) PBArray *	varintArray;
+@property (nonatomic,strong,readonly) PBArray *	fixed32Array;
+@property (nonatomic,strong,readonly) PBArray *	fixed64Array;
+@property (nonatomic,strong,readonly) NSArray *	lengthDelimitedArray;
+@property (nonatomic,strong,readonly) NSArray *	groupArray;
+
++ (PBField *)defaultInstance;
+
+- (SInt32)getSerializedSize:(SInt32)fieldNumber;
+- (SInt32)getSerializedSizeAsMessageSetExtension:(SInt32)fieldNumber;
+
+- (void)writeTo:(SInt32) fieldNumber output:(PBCodedOutputStream *)output;
+- (void)writeAsMessageSetExtensionTo:(SInt32)fieldNumber output:(PBCodedOutputStream *)output;
+- (void)writeDescriptionFor:(SInt32) fieldNumber
+                         to:(NSMutableString*) output
+                 withIndent:(NSString*) indent;
+@end
diff --git a/src/runtime/Classes/Field.m b/src/runtime/Classes/Field.m
new file mode 100755
index 0000000..2bf76b1
--- /dev/null
+++ b/src/runtime/Classes/Field.m
@@ -0,0 +1,159 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Field.h"
+
+#import "CodedOutputStream.h"
+#import "PBArray.h"
+#import "UnknownFieldSet.h"
+#import "Utilities.h"
+
+@implementation PBField
+
+@synthesize varintArray = _varintArray;
+@synthesize fixed32Array = _fixed32Array;
+@synthesize fixed64Array = _fixed64Array;
+@synthesize lengthDelimitedArray = _lengthDelimitedArray;
+@synthesize groupArray = _groupArray;
+
+static PBField *sDefaultInstance = nil;
+
++ (void)initialize {
+	if (self == [PBField class]) {
+		sDefaultInstance = [[PBField alloc] init];
+	}
+}
+
+
++ (PBField *)defaultInstance {
+	return sDefaultInstance;
+}
+
+- (SInt32)getSerializedSize:(SInt32)fieldNumber {
+	SInt32 result = 0;
+
+	const SInt64 *varintValues = (const SInt64 *)_varintArray.data;
+	if (varintValues) {
+		const NSUInteger count = _varintArray.count;
+		for (UInt32 i = 0; i < count; ++i) {
+			result += computeInt64Size(fieldNumber, varintValues[i]);
+		}
+	}
+
+	const SInt32 *fixed32Values = (const SInt32 *)_fixed32Array.data;
+	if (fixed32Values) {
+		const NSUInteger count = _fixed32Array.count;
+		for (UInt32 i = 0; i < count; ++i) {
+			result += computeFixed32Size(fieldNumber, fixed32Values[i]);
+		}
+	}
+
+	const SInt64 *fixed64Values = (const SInt64 *)_fixed64Array.data;
+	if (fixed64Values) {
+		const NSUInteger count = _fixed64Array.count;
+		for (NSUInteger i = 0; i < count; ++i) {
+			result += computeFixed64Size(fieldNumber, fixed64Values[i]);
+		}
+	}
+
+	for (NSData *value in _lengthDelimitedArray) {
+		result += computeDataSize(fieldNumber, value);
+	}
+
+	for (PBUnknownFieldSet *value in _groupArray) {
+		result += computeUnknownGroupSize(fieldNumber, value);
+	}
+
+	return result;
+}
+
+- (SInt32)getSerializedSizeAsMessageSetExtension:(SInt32)fieldNumber {
+	SInt32 result = 0;
+
+	for (NSData *value in _lengthDelimitedArray) {
+		result += computeRawMessageSetExtensionSize(fieldNumber, value);
+	}
+
+	return result;
+}
+
+- (void)writeTo:(SInt32)fieldNumber output:(PBCodedOutputStream *) output {
+	const SInt64 *varintValues = (const SInt64 *)_varintArray.data;
+	if (varintValues) {
+		const NSUInteger count = _varintArray.count;
+		for (NSUInteger i = 0; i < count; ++i) {
+			[output writeInt64:fieldNumber value:varintValues[i]];
+		}
+	}
+
+	const SInt32 *fixed32Values = (const SInt32 *)_fixed32Array.data;
+	if (fixed32Values) {
+		const NSUInteger count = _fixed32Array.count;
+		for (NSUInteger i = 0; i < count; ++i) {
+			[output writeFixed32:fieldNumber value:fixed32Values[i]];
+		}
+	}
+
+	const SInt64 *fixed64Values = (const SInt64 *)_fixed64Array.data;
+	if (fixed64Values) {
+		const NSUInteger count = _fixed64Array.count;
+		for (NSUInteger i = 0; i < count; ++i) {
+			[output writeFixed64:fieldNumber value:fixed64Values[i]];
+		}
+	}
+
+	for (NSData *value in _lengthDelimitedArray) {
+		[output writeData:fieldNumber value:value];
+	}
+
+	for (PBUnknownFieldSet *value in _groupArray) {
+		[output writeUnknownGroup:fieldNumber value:value];
+	}
+}
+
+- (void)writeDescriptionFor:(SInt32) fieldNumber
+                         to:(NSMutableString*) output
+                 withIndent:(NSString*) indent {
+    [self.varintArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+        
+    }];
+    [self.varintArray enumerateObjectsUsingBlock:^(NSNumber* value, NSUInteger idx, BOOL *stop) {
+        [output appendFormat:@"%@%ld: %qi\n", indent, (long)fieldNumber, value.longLongValue];
+    }];
+    [self.fixed32Array enumerateObjectsUsingBlock:^(NSNumber* value, NSUInteger idx, BOOL *stop) {
+        [output appendFormat:@"%@%ld: %ld\n", indent, (long)fieldNumber, (long)value.integerValue];
+    }];
+    [self.fixed64Array enumerateObjectsUsingBlock:^(NSNumber* value, NSUInteger idx, BOOL *stop) {
+         [output appendFormat:@"%@%ld: %lld\n", indent, (long)fieldNumber, value.longLongValue];
+    }];
+      for (NSData* value in self.lengthDelimitedArray) {
+        [output appendFormat:@"%@%ld: %@\n", indent, (long)fieldNumber, value];
+      }
+      for (PBUnknownFieldSet* value in self.groupArray) {
+        [output appendFormat:@"%@%ld: [\n", indent, (long)fieldNumber];
+        [value writeDescriptionTo:output withIndent:[NSString stringWithFormat:@"%@  ", indent]];
+        [output appendFormat:@"%@]", indent];
+      }
+}
+
+- (void)writeAsMessageSetExtensionTo:(SInt32)fieldNumber output:(PBCodedOutputStream *) output {
+	for (NSData *value in _lengthDelimitedArray) {
+		[output writeRawMessageSetExtension:fieldNumber value:value];
+	}
+}
+
+@end
\ No newline at end of file
diff --git a/src/runtime/Classes/ForwardDeclarations.h b/src/runtime/Classes/ForwardDeclarations.h
new file mode 100755
index 0000000..cd776e3
--- /dev/null
+++ b/src/runtime/Classes/ForwardDeclarations.h
@@ -0,0 +1,35 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+@protocol PBMessage;
+@protocol PBMessageBuilder;
+@protocol PBExtensionField;
+
+@class PBAbstractMessage;
+@class PBCodedInputStream;
+@class PBCodedOutputStream;
+@class PBConcreteExtensionField;
+@class PBExtendableMessageBuilder;
+@class PBExtendableMessage;
+@class PBExtensionRegistry;
+@class PBField;
+@class PBGeneratedMessage;
+@class PBGeneratedMessageBuilder;
+@class PBMutableExtensionRegistry;
+@class PBMutableField;
+@class PBUnknownFieldSet;
+@class PBUnknownFieldSetBuilder;
diff --git a/src/runtime/Classes/GeneratedMessage.h b/src/runtime/Classes/GeneratedMessage.h
new file mode 100755
index 0000000..c94a265
--- /dev/null
+++ b/src/runtime/Classes/GeneratedMessage.h
@@ -0,0 +1,36 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "AbstractMessage.h"
+
+/**
+ * All generated protocol message classes extend this class.  This class
+ * implements most of the Message and Builder interfaces using Java reflection.
+ * Users can ignore this class and pretend that generated messages implement
+ * the Message interface directly.
+ *
+ * @author Cyrus Najmabadi
+ */
+@interface PBGeneratedMessage : PBAbstractMessage {
+@private
+  PBUnknownFieldSet* unknownFields;
+
+@protected
+  SInt32 memoizedSerializedSize;
+}
+
+@end
diff --git a/src/runtime/Classes/GeneratedMessage.m b/src/runtime/Classes/GeneratedMessage.m
new file mode 100755
index 0000000..08e4dd8
--- /dev/null
+++ b/src/runtime/Classes/GeneratedMessage.m
@@ -0,0 +1,40 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "GeneratedMessage.h"
+
+#import "UnknownFieldSet.h"
+
+@interface PBGeneratedMessage ()
+@property (strong) PBUnknownFieldSet* unknownFields;
+@end
+
+
+@implementation PBGeneratedMessage
+
+@synthesize unknownFields;
+
+- (id) init {
+  if ((self = [super init])) {
+    self.unknownFields = [PBUnknownFieldSet defaultInstance];
+    memoizedSerializedSize = -1;
+  }
+
+  return self;
+}
+
+@end
diff --git a/src/runtime/Classes/GeneratedMessageBuilder.h b/src/runtime/Classes/GeneratedMessageBuilder.h
new file mode 100755
index 0000000..a8c84f4
--- /dev/null
+++ b/src/runtime/Classes/GeneratedMessageBuilder.h
@@ -0,0 +1,33 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "AbstractMessageBuilder.h"
+
+@class PBUnknownFieldSetBuilder;
+
+@interface PBGeneratedMessageBuilder : PBAbstractMessageBuilder {
+}
+
+/* @protected */
+- (BOOL) parseUnknownField:(PBCodedInputStream*) input
+             unknownFields:(PBUnknownFieldSetBuilder*) unknownFields
+         extensionRegistry:(PBExtensionRegistry*) extensionRegistry
+                       tag:(SInt32) tag;
+
+- (void) checkInitialized;
+
+@end
diff --git a/src/runtime/Classes/GeneratedMessageBuilder.m b/src/runtime/Classes/GeneratedMessageBuilder.m
new file mode 100755
index 0000000..09fe852
--- /dev/null
+++ b/src/runtime/Classes/GeneratedMessageBuilder.m
@@ -0,0 +1,95 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "GeneratedMessageBuilder.h"
+
+#import "GeneratedMessage.h"
+#import "Message.h"
+#import "MessageBuilder.h"
+#import "UnknownFieldSet.h"
+#import "UnknownFieldSetBuilder.h"
+
+
+@interface PBGeneratedMessage ()
+@property (strong) PBUnknownFieldSet* unknownFields;
+@end
+
+
+@implementation PBGeneratedMessageBuilder
+
+/**
+ * Get the message being built.  We don't just pass this to the
+ * constructor because it becomes null when build() is called.
+ */
+- (PBGeneratedMessage*) internalGetResult {
+  @throw [NSException exceptionWithName:@"ImproperSubclassing" reason:@"" userInfo:nil];
+}
+
+
+- (void) checkInitialized {
+  PBGeneratedMessage* result = self.internalGetResult;
+  if (result != nil && !result.isInitialized) {
+    @throw [NSException exceptionWithName:@"UninitializedMessage" reason:@"" userInfo:nil];
+  }
+}
+
+
+- (PBUnknownFieldSet*) unknownFields {
+  return self.internalGetResult.unknownFields;
+}
+
+
+- (id<PBMessageBuilder>) setUnknownFields:(PBUnknownFieldSet*) unknownFields {
+  self.internalGetResult.unknownFields = unknownFields;
+  return self;
+}
+
+
+- (id<PBMessageBuilder>) mergeUnknownFields:(PBUnknownFieldSet*) unknownFields {
+  PBGeneratedMessage* result = self.internalGetResult;
+  result.unknownFields =
+  [[[PBUnknownFieldSet builderWithUnknownFields:result.unknownFields]
+    mergeUnknownFields:unknownFields] build];
+  return self;
+}
+
+
+- (BOOL) isInitialized {
+  return self.internalGetResult.isInitialized;
+}
+
+
+/**
+ * Called by subclasses to parse an unknown field.
+ * @return {@code YES} unless the tag is an end-group tag.
+ */
+- (BOOL) parseUnknownField:(PBCodedInputStream*) input
+             unknownFields:(PBUnknownFieldSetBuilder*) unknownFields
+         extensionRegistry:(PBExtensionRegistry*) extensionRegistry
+                       tag:(SInt32) tag {
+  return [unknownFields mergeFieldFrom:tag input:input];
+}
+
+
+- (void) checkInitializedParsed {
+  PBGeneratedMessage* result = self.internalGetResult;
+  if (result != nil && !result.isInitialized) {
+    @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"" userInfo:nil];
+  }
+}
+
+@end
diff --git a/src/runtime/Classes/Message.h b/src/runtime/Classes/Message.h
new file mode 100755
index 0000000..e488e9e
--- /dev/null
+++ b/src/runtime/Classes/Message.h
@@ -0,0 +1,85 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+@class PBCodedOutputStream;
+@class PBUnknownFieldSet;
+@protocol PBMessageBuilder;
+
+/**
+ * Abstract interface implemented by Protocol Message objects.
+ *
+ * @author Cyrus Najmabadi
+ */
+@protocol PBMessage<NSObject>
+/**
+ * Get an instance of the type with all fields set to their default values.
+ * This may or may not be a singleton.  This differs from the
+ * {@code getDefaultInstance()} method of generated message classes in that
+ * this method is an abstract method of the {@code Message} interface
+ * whereas {@code getDefaultInstance()} is a static method of a specific
+ * class.  They return the same thing.
+ */
+- (id<PBMessage>) defaultInstance;
+
+/**
+ * Get the {@code UnknownFieldSet}
+ */
+- (PBUnknownFieldSet*) unknownFields;
+
+/**
+ * Get the number of bytes required to encode this message.  The result
+ * is only computed on the first call and memoized after that.
+ */
+- (SInt32) serializedSize;
+
+/**
+ * Returns true if all required fields in the message and all embedded
+ * messages are set, false otherwise.
+ */
+- (BOOL) isInitialized;
+
+/**
+ * Serializes the message and writes it to {@code output}.  This does not
+ * flush or close the stream.
+ */
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (void) writeToOutputStream:(NSOutputStream*) output;
+
+/**
+ * Serializes the message to a {@code ByteString} and returns it. This is
+ * just a trivial wrapper around
+ * {@link #writeTo(CodedOutputStream)}.
+ */
+- (NSData*) data;
+
+/**
+ * Constructs a new builder for a message of the same type as this message.
+ */
+- (id<PBMessageBuilder>) builder;
+
+/**
+ * Constructs a builder initialized with the current message.  Use this to
+ * derive a new message from the current one.
+ */
+- (id<PBMessageBuilder>) toBuilder;
+
+/**
+ * Returns a string description of the message.
+ */
+- (NSString*) description;
+
+@end
diff --git a/src/runtime/Classes/MessageBuilder.h b/src/runtime/Classes/MessageBuilder.h
new file mode 100755
index 0000000..d7d7d2a
--- /dev/null
+++ b/src/runtime/Classes/MessageBuilder.h
@@ -0,0 +1,136 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Message.h"
+
+@class PBCodedInputStream;
+@class PBExtensionRegistry;
+
+/**
+ * Abstract interface implemented by Protocol Message builders.
+ */
+@protocol PBMessageBuilder<NSObject>
+/** Resets all fields to their default values. */
+- (id<PBMessageBuilder>) clear;
+
+/**
+ * Construct the final message.  Once this is called, the Builder is no
+ * longer valid, and calling any other method may throw a
+ * NullPointerException.  If you need to continue working with the builder
+ * after calling {@code build()}, {@code clone()} it first.
+ * @throws UninitializedMessageException The message is missing one or more
+ *         required fields (i.e. {@link #isInitialized()} returns false).
+ *         Use {@link #buildPartial()} to bypass this check.
+ */
+- (id<PBMessage>) build;
+
+/**
+ * Like {@link #build()}, but does not throw an exception if the message
+ * is missing required fields.  Instead, a partial message is returned.
+ */
+- (id<PBMessage>) buildPartial;
+- (id<PBMessageBuilder>) clone;
+
+/**
+ * Returns true if all required fields in the message and all embedded
+ * messages are set, false otherwise.
+ */
+- (BOOL) isInitialized;
+
+/**
+ * Get the message's type's default instance.
+ * See {@link Message#getDefaultInstanceForType()}.
+ */
+- (id<PBMessage>) defaultInstance;
+
+- (PBUnknownFieldSet*) unknownFields;
+- (id<PBMessageBuilder>) setUnknownFields:(PBUnknownFieldSet*) unknownFields;
+
+/**
+ * Merge some unknown fields into the {@link UnknownFieldSet} for this
+ * message.
+ */
+- (id<PBMessageBuilder>) mergeUnknownFields:(PBUnknownFieldSet*) unknownFields;
+
+/**
+ * Parses a message of this type from the input and merges it with this
+ * message, as if using {@link Builder#mergeFrom(Message)}.
+ *
+ * <p>Warning:  This does not verify that all required fields are present in
+ * the input message.  If you call {@link #build()} without setting all
+ * required fields, it will throw an {@link UninitializedMessageException},
+ * which is a {@code RuntimeException} and thus might not be caught.  There
+ * are a few good ways to deal with this:
+ * <ul>
+ *   <li>Call {@link #isInitialized()} to verify that all required fields
+ *       are set before building.
+ *   <li>Parse the message separately using one of the static
+ *       {@code parseFrom} methods, then use {@link #mergeFrom(Message)}
+ *       to merge it with this one.  {@code parseFrom} will throw an
+ *       {@link InvalidProtocolBufferException} (an {@code IOException})
+ *       if some required fields are missing.
+ *   <li>Use {@code buildPartial()} to build, which ignores missing
+ *       required fields.
+ * </ul>
+ *
+ * <p>Note:  The caller should call
+ * {@link CodedInputStream#checkLastTagWas(int)} after calling this to
+ * verify that the last tag seen was the appropriate end-group tag,
+ * or zero for EOF.
+ */
+- (id<PBMessageBuilder>) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+
+/**
+ * Like {@link Builder#mergeFrom(CodedInputStream)}, but also
+ * parses extensions.  The extensions that you want to be able to parse
+ * must be registered in {@code extensionRegistry}.  Extensions not in
+ * the registry will be treated as unknown fields.
+ */
+- (id<PBMessageBuilder>) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+/**
+ * Parse {@code data} as a message of this type and merge it with the
+ * message being built.  This is just a small wrapper around
+ * {@link #mergeFrom(CodedInputStream)}.
+ */
+- (id<PBMessageBuilder>) mergeFromData:(NSData*) data;
+
+/**
+ * Parse {@code data} as a message of this type and merge it with the
+ * message being built.  This is just a small wrapper around
+ * {@link #mergeFrom(CodedInputStream,ExtensionRegistry)}.
+ */
+- (id<PBMessageBuilder>) mergeFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+
+/**
+ * Parse a message of this type from {@code input} and merge it with the
+ * message being built.  This is just a small wrapper around
+ * {@link #mergeFrom(CodedInputStream)}.  Note that this method always
+ * reads the <i>entire</i> input (unless it throws an exception).  If you
+ * want it to stop earlier, you will need to wrap your input in some
+ * wrapper stream that limits reading.  Despite usually reading the entire
+ * input, this does not close the stream.
+ */
+- (id<PBMessageBuilder>) mergeFromInputStream:(NSInputStream*) input;
+
+/**
+ * Parse a message of this type from {@code input} and merge it with the
+ * message being built.  This is just a small wrapper around
+ * {@link #mergeFrom(CodedInputStream,ExtensionRegistry)}.
+ */
+- (id<PBMessageBuilder>) mergeFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry;
+@end
diff --git a/src/runtime/Classes/MutableExtensionRegistry.h b/src/runtime/Classes/MutableExtensionRegistry.h
new file mode 100755
index 0000000..dcb97a3
--- /dev/null
+++ b/src/runtime/Classes/MutableExtensionRegistry.h
@@ -0,0 +1,29 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "ExtensionRegistry.h"
+
+@interface PBMutableExtensionRegistry : PBExtensionRegistry {
+@private
+  NSMutableDictionary* mutableClassMap;
+}
+
++ (PBMutableExtensionRegistry*) registry;
+
+- (void) addExtension:(id<PBExtensionField>) extension;
+
+@end
diff --git a/src/runtime/Classes/MutableExtensionRegistry.m b/src/runtime/Classes/MutableExtensionRegistry.m
new file mode 100755
index 0000000..37e6b4b
--- /dev/null
+++ b/src/runtime/Classes/MutableExtensionRegistry.m
@@ -0,0 +1,65 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "MutableExtensionRegistry.h"
+
+#import "ExtensionField.h"
+
+@interface PBMutableExtensionRegistry()
+@property (strong) NSMutableDictionary* mutableClassMap;
+@end
+
+@implementation PBMutableExtensionRegistry
+
+@synthesize mutableClassMap;
+
+
+
+- (id) initWithClassMap:(NSMutableDictionary*) mutableClassMap_ {
+  if ((self = [super initWithClassMap:mutableClassMap_])) {
+    self.mutableClassMap = mutableClassMap_;
+  }
+
+  return self;
+}
+
+
++ (PBMutableExtensionRegistry*) registry {
+    return [[PBMutableExtensionRegistry alloc] initWithClassMap:[NSMutableDictionary dictionary]];
+}
+
+
+- (void) addExtension:(id<PBExtensionField>) extension {
+  if (extension == nil) {
+    return;
+  }
+
+  Class extendedClass = [extension extendedClass];
+  id key = [self keyForClass:extendedClass];
+
+  NSMutableDictionary* extensionMap = [classMap objectForKey:key];
+  if (extensionMap == nil) {
+    extensionMap = [NSMutableDictionary dictionary];
+    [mutableClassMap setObject:extensionMap forKey:key];
+  }
+
+  [extensionMap setObject:extension
+                   forKey:[NSNumber numberWithInteger:[extension fieldNumber]]];
+}
+
+
+@end
diff --git a/src/runtime/Classes/MutableField.h b/src/runtime/Classes/MutableField.h
new file mode 100755
index 0000000..c2096bd
--- /dev/null
+++ b/src/runtime/Classes/MutableField.h
@@ -0,0 +1,35 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Field.h"
+
+@class PBUnknownFieldSet;
+
+@interface PBMutableField : PBField
+
++ (PBMutableField *)field;
+
+- (PBMutableField *)mergeFromField:(PBField *)other;
+
+- (PBMutableField *)clear;
+- (PBMutableField *)addVarint:(SInt64)value;
+- (PBMutableField *)addFixed32:(SInt32)value;
+- (PBMutableField *)addFixed64:(SInt64)value;
+- (PBMutableField *)addLengthDelimited:(NSData *)value;
+- (PBMutableField *)addGroup:(PBUnknownFieldSet *)value;
+
+@end
\ No newline at end of file
diff --git a/src/runtime/Classes/MutableField.m b/src/runtime/Classes/MutableField.m
new file mode 100755
index 0000000..843da43
--- /dev/null
+++ b/src/runtime/Classes/MutableField.m
@@ -0,0 +1,130 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "MutableField.h"
+
+#import "Field.h"
+#import "PBArray.h"
+
+@implementation PBMutableField
+
+
++ (PBMutableField *)field {
+	return [[PBMutableField alloc] init];
+}
+
+- (PBMutableField *)clear {
+
+    _varintArray = nil;
+	_fixed32Array = nil;
+    _fixed64Array = nil;
+    _lengthDelimitedArray = nil;
+    _groupArray = nil;
+
+	return self;
+}
+
+- (PBMutableField *)mergeFromField:(PBField *)other {
+	if (other.varintArray.count > 0) {
+		if (_varintArray == nil) {
+			_varintArray = [other.varintArray copy];
+		} else {
+			[_varintArray appendArray:other.varintArray];
+		}
+	}
+
+	if (other.fixed32Array.count > 0) {
+		if (_fixed32Array == nil) {
+			_fixed32Array = [other.fixed32Array copy];
+		} else {
+			[_fixed32Array appendArray:other.fixed32Array];
+		}
+	}
+
+	if (other.fixed64Array.count > 0) {
+		if (_fixed64Array == nil) {
+			_fixed64Array = [other.fixed64Array copy];
+		} else {
+			[_fixed64Array appendArray:other.fixed64Array];
+		}
+	}
+
+	if (other.lengthDelimitedArray.count > 0) {
+		if (_lengthDelimitedArray == nil) {
+			_lengthDelimitedArray = [other.lengthDelimitedArray copy];
+		} else {
+			[_lengthDelimitedArray addObjectsFromArray:other.lengthDelimitedArray];
+		}
+	}
+
+	if (other.groupArray.count > 0) {
+		if (_groupArray == nil) {
+			_groupArray = [other.groupArray copy];
+		} else {
+			[_groupArray addObjectsFromArray:other.groupArray];
+		}
+	}
+
+	return self;
+}
+
+- (PBMutableField *)addVarint:(SInt64)value {
+	if (_varintArray == nil) {
+		_varintArray = [[PBAppendableArray alloc] initWithValueType:PBArrayValueTypeInt64];
+	}
+	[_varintArray addInt64:value];
+
+	return self;
+}
+
+- (PBMutableField *)addFixed32:(SInt32)value {
+	if (_fixed32Array == nil) {
+		_fixed32Array = [[PBAppendableArray alloc] initWithValueType:PBArrayValueTypeInt32];
+	}
+	[_fixed32Array addInt32:value];
+
+	return self;
+}
+
+- (PBMutableField *)addFixed64:(SInt64)value {
+	if (_fixed64Array == nil) {
+		_fixed64Array = [[PBAppendableArray alloc] initWithValueType:PBArrayValueTypeInt64];
+	}
+	[_fixed64Array addInt64:value];
+
+	return self;
+}
+
+- (PBMutableField *)addLengthDelimited:(NSData *)value {
+	if (_lengthDelimitedArray == nil) {
+		_lengthDelimitedArray = [[NSMutableArray alloc] init];
+	}
+	[_lengthDelimitedArray addObject:value];
+
+	return self;
+}
+
+- (PBMutableField *)addGroup:(PBUnknownFieldSet *)value {
+	if (_groupArray == nil) {
+		_groupArray = [[NSMutableArray alloc] init];
+	}
+	[_groupArray addObject:value];
+
+	return self;
+}
+
+@end
\ No newline at end of file
diff --git a/src/runtime/Classes/PBArray.h b/src/runtime/Classes/PBArray.h
new file mode 100755
index 0000000..fa720cb
--- /dev/null
+++ b/src/runtime/Classes/PBArray.h
@@ -0,0 +1,106 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+// Author: Jon Parise <jon@booyah.com>
+
+#import <Foundation/Foundation.h>
+
+extern NSString * const PBArrayTypeMismatchException;
+extern NSString * const PBArrayNumberExpectedException;
+extern NSString * const PBArrayAllocationFailureException;
+
+typedef enum _PBArrayValueType
+{
+	PBArrayValueTypeBool,
+	PBArrayValueTypeInt32,
+	PBArrayValueTypeUInt32,
+	PBArrayValueTypeInt64,
+	PBArrayValueTypeUInt64,
+	PBArrayValueTypeFloat,
+	PBArrayValueTypeDouble,
+} PBArrayValueType;
+
+// PBArray is an immutable array class that's optimized for storing primitive
+// values.  All values stored in an PBArray instance must have the same type
+// (PBArrayValueType).  Object values (PBArrayValueTypeObject) are retained.
+@interface PBArray : NSObject <NSCopying>
+{
+@protected
+	PBArrayValueType	_valueType;
+	NSUInteger			_capacity;
+	NSUInteger			_count;
+	void *				_data;
+
+}
+
+- (NSUInteger)count;
+- (BOOL)boolAtIndex:(NSUInteger)index;
+- (SInt32)int32AtIndex:(NSUInteger)index;
+- (SInt32)enumAtIndex:(NSUInteger)index;
+- (UInt32)uint32AtIndex:(NSUInteger)index;
+- (SInt64)int64AtIndex:(NSUInteger)index;
+- (UInt64)uint64AtIndex:(NSUInteger)index;
+- (Float32)floatAtIndex:(NSUInteger)index;
+- (Float64)doubleAtIndex:(NSUInteger)index;
+- (BOOL)isEqualToArray:(PBArray *)array;
+- (void)enumerateObjectsUsingBlock:(void (^)(id obj, NSUInteger idx, BOOL *stop))block;
+- (NSUInteger)indexOfObjectPassingTest:(BOOL (^)(id obj, NSUInteger idx, BOOL *stop))predicate;
+
+//This Methods automaticaly pack/unpack in NSNumber primitive values
+- (id)firstObject;
+- (id)lastObject;
+- (id)objectAtIndexedSubscript:(NSUInteger)idx;
+
+@property (nonatomic,assign,readonly) PBArrayValueType valueType;
+@property (nonatomic,assign,readonly) const void * data;
+@property (nonatomic,assign,readonly,getter=count) NSUInteger count;
+
+@end
+
+@interface PBArray (PBArrayExtended)
+
+- (id)arrayByAppendingArray:(PBArray *)array;
+- (PBArray *)filteredArrayUsingPredicate:(NSPredicate *)predicate;
+@end
+
+@interface PBArray (PBArrayCreation)
+
++ (id)arrayWithValueType:(PBArrayValueType)valueType;
++ (id)arrayWithValues:(const void *)values count:(NSUInteger)count valueType:(PBArrayValueType)valueType;
++ (id)arrayWithArray:(NSArray *)array valueType:(PBArrayValueType)valueType;
+- (id)initWithValueType:(PBArrayValueType)valueType;
+- (id)initWithValues:(const void *)values count:(NSUInteger)count valueType:(PBArrayValueType)valueType;
+- (id)initWithArray:(NSArray *)array valueType:(PBArrayValueType)valueType;
+
+@end
+
+// PBAppendableArray extends PBArray with the ability to append new values to
+// the end of the array.
+@interface PBAppendableArray : PBArray
+
+- (void)addBool:(BOOL)value;
+- (void)addInt32:(SInt32)value;
+- (void)addUint32:(UInt32)value;
+- (void)addInt64:(SInt64)value;
+- (void)addUint64:(UInt64)value;
+- (void)addFloat:(Float32)value;
+- (void)addDouble:(Float64)value;
+- (void)addEnum:(SInt32)value;
+
+- (void)appendArray:(PBArray *)array;
+- (void)appendValues:(const void *)values count:(UInt32)count;
+
+@end
diff --git a/src/runtime/Classes/PBArray.m b/src/runtime/Classes/PBArray.m
new file mode 100755
index 0000000..b587e8d
--- /dev/null
+++ b/src/runtime/Classes/PBArray.m
@@ -0,0 +1,575 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+// Author: Jon Parise <jon@booyah.com>
+
+#import "PBArray.h"
+
+NSString * const PBArrayTypeMismatchException = @"PBArrayTypeMismatchException";
+NSString * const PBArrayNumberExpectedException = @"PBArrayNumberExpectedException";
+NSString * const PBArrayAllocationFailureException = @"PBArrayAllocationFailureException";
+
+#pragma mark NSNumber Setters
+
+typedef void (*PBArrayValueSetter)(NSNumber *number, void *value);
+
+static void PBArraySetBoolValue(NSNumber *number, void *value)
+{
+	*((BOOL *)value) = [number charValue];
+}
+
+static void PBArraySetInt32Value(NSNumber *number, void *value)
+{
+	*((SInt32 *)value) = (SInt32)[number integerValue];
+}
+
+static void PBArraySetUInt32Value(NSNumber *number, void *value)
+{
+	*((UInt32 *)value) = (UInt32)[number unsignedIntegerValue];
+}
+
+static void PBArraySetInt64Value(NSNumber *number, void *value)
+{
+	*((SInt64 *)value) = (SInt64)[number longLongValue];
+}
+
+static void PBArraySetUInt64Value(NSNumber *number, void *value)
+{
+	*((UInt64 *)value) = (UInt64)[number unsignedLongLongValue];
+}
+
+static void PBArraySetFloatValue(NSNumber *number, void *value)
+{
+	*((Float32 *)value) = [number floatValue];
+}
+
+static void PBArraySetDoubleValue(NSNumber *number, void *value)
+{
+	*((Float64 *)value) = [number doubleValue];
+}
+
+#pragma mark Array Value Types
+
+typedef struct _PBArrayValueTypeInfo
+{
+	const size_t size;
+	const PBArrayValueSetter setter;
+    
+} PBArrayValueTypeInfo;
+
+static PBArrayValueTypeInfo PBValueTypes[] =
+{
+	{ sizeof(BOOL),		PBArraySetBoolValue		},
+	{ sizeof(SInt32),	PBArraySetInt32Value	},
+	{ sizeof(UInt32),	PBArraySetUInt32Value	},
+	{ sizeof(SInt64),	PBArraySetInt64Value	},
+	{ sizeof(UInt64),	PBArraySetUInt64Value	},
+	{ sizeof(Float32),	PBArraySetFloatValue	},
+	{ sizeof(Float64),	PBArraySetDoubleValue	},
+};
+
+#define PBArrayValueTypeSize(type)		PBValueTypes[type].size
+#define PBArrayValueTypeSetter(type)	PBValueTypes[type].setter
+
+#pragma mark Helper Macros
+
+#define PBArraySlot(index) (_data + (index * PBArrayValueTypeSize(_valueType)))
+
+#define PBArrayForEachObject(__data, __count, x) \
+	if (_valueType == PBArrayValueTypeObject) \
+		for (NSUInteger i = 0; i < __count; ++i) { id object = ((id *)__data)[i]; [object x]; }
+
+#define PBArrayValueTypeAssert(type) \
+	if (__builtin_expect(_valueType != type, 0)) \
+		[NSException raise:PBArrayTypeMismatchException \
+					format:@"array value type mismatch (expected '%s')", #type];
+
+#define PBArrayValueRangeAssert(index) \
+	if (__builtin_expect(index >= _count, 0)) \
+		[NSException raise:NSRangeException format: @"index (%lu) beyond bounds (%lu)", (unsigned long)index, (unsigned long)_count];
+
+#define PBArrayNumberAssert(value) \
+	if (__builtin_expect(![value isKindOfClass:[NSNumber class]], 0)) \
+		[NSException raise:PBArrayNumberExpectedException format:@"NSNumber expected (got '%@')", [value class]];
+
+#define PBArrayAllocationAssert(p, size) \
+	if (__builtin_expect(p == NULL, 0)) \
+		[NSException raise:PBArrayAllocationFailureException format:@"failed to allocate %lu bytes", size];
+
+#pragma mark -
+#pragma mark PBArray
+
+@implementation PBArray
+
+@synthesize valueType = _valueType;
+@dynamic data;
+
+- (id)initWithCount:(NSUInteger)count valueType:(PBArrayValueType)valueType
+{
+	if ((self = [super init]))
+	{
+		_valueType = valueType;
+		_count = count;
+		_capacity = count;
+        
+		if (_capacity)
+		{
+            _data = malloc(_capacity * PBArrayValueTypeSize(_valueType));
+            if (_data == NULL)
+            {
+                self = nil;
+            }
+		}
+	}
+    
+	return self;
+}
+
+- (id)copyWithZone:(NSZone *)zone
+{
+	PBArray *copy = [[[self class] allocWithZone:zone] initWithCount:_count valueType:_valueType];
+	if (copy)
+	{
+		memcpy(copy->_data, _data, _count * PBArrayValueTypeSize(_valueType));
+	}
+
+	return copy;
+}
+
+
+- (NSString *)description
+{
+	return [NSString stringWithFormat:@"<%@ %p>{valueType = %d, count = %ld, capacity = %ld, data = %p}",
+			[self class], self, _valueType, (long)_count, (long)_capacity, _data];
+}
+
+- (NSUInteger)count
+{
+	return _count;
+}
+
+- (const void *)data
+{
+	return _data;
+}
+
+- (BOOL)boolAtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert(index);
+	PBArrayValueTypeAssert(PBArrayValueTypeBool);
+	return ((BOOL *)_data)[index];
+}
+
+- (SInt32)int32AtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert((unsigned long)index);
+	PBArrayValueTypeAssert(PBArrayValueTypeInt32);
+	return ((SInt32 *)_data)[index];
+}
+
+- (UInt32)uint32AtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert((unsigned long)index);
+	PBArrayValueTypeAssert(PBArrayValueTypeUInt32);
+	return ((UInt32 *)_data)[index];
+}
+
+- (SInt32)enumAtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert(index);
+	PBArrayValueTypeAssert(PBArrayValueTypeInt32);
+	return ((SInt32 *)_data)[index];
+}
+
+
+- (SInt64)int64AtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert(index);
+	PBArrayValueTypeAssert(PBArrayValueTypeInt64);
+	return ((SInt64 *)_data)[index];
+}
+
+- (UInt64)uint64AtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert(index);
+	PBArrayValueTypeAssert(PBArrayValueTypeUInt64);
+	return ((UInt64 *)_data)[index];
+}
+
+- (Float32)floatAtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert(index);
+	PBArrayValueTypeAssert(PBArrayValueTypeFloat);
+	return ((Float32 *)_data)[index];
+}
+
+- (Float64)doubleAtIndex:(NSUInteger)index
+{
+	PBArrayValueRangeAssert(index);
+	PBArrayValueTypeAssert(PBArrayValueTypeDouble);
+	return ((Float64 *)_data)[index];
+}
+
+- (BOOL)isEqualToArray:(PBArray *)array
+{
+	if (self == array)
+	{
+		return YES;
+	}
+	else if (array->_count != _count)
+	{
+		return NO;
+	}
+	else
+	{
+		return memcmp(array->_data, _data, _count * PBArrayValueTypeSize(_valueType)) == 0;
+	}
+}
+
+- (BOOL)isEqual:(id)object
+{
+	BOOL equal = NO;
+	if ([object isKindOfClass:[PBArray class]])
+	{
+		equal = [self isEqualToArray:object];
+	}
+	return equal;
+}
+
+-(id)firstObject
+{
+    if (self.count>0) {
+        return [self objectAtIndexedSubscript:0];
+    }
+    return nil;
+}
+
+-(id)lastObject
+{
+    if (self.count>0) {
+        return [self objectAtIndexedSubscript:self.count - 1];
+    }
+    return nil;
+}
+
+- (id)objectAtIndexedSubscript:(NSUInteger)idx
+{
+ 
+    if (idx < self.count) {
+        if (PBArrayValueTypeBool == _valueType)
+        {
+            return [NSNumber numberWithBool:[self boolAtIndex:idx]];
+        }
+        else if (PBArrayValueTypeInt32 == _valueType)
+        {
+            return [NSNumber numberWithLong:[self int32AtIndex:idx]];
+        }
+        else if (PBArrayValueTypeInt64 == _valueType)
+        {
+            return [NSNumber numberWithLongLong:[self int64AtIndex:idx]];
+        }
+        else if (PBArrayValueTypeUInt32 == _valueType)
+        {
+            return [NSNumber numberWithUnsignedLong:[self uint32AtIndex:idx]];
+        }
+        else if (PBArrayValueTypeUInt64 == _valueType)
+        {
+            return [NSNumber numberWithUnsignedLongLong:[self uint64AtIndex:idx]];
+        }
+        else if (_valueType == PBArrayValueTypeFloat)
+        {
+            return [NSNumber numberWithFloat:[self floatAtIndex:idx]];
+        }
+        else if (_valueType == PBArrayValueTypeDouble)
+        {
+            return [NSNumber numberWithDouble:[self doubleAtIndex:idx]];
+        }
+    }
+    return nil;
+
+}
+
+
+
+- (void)enumerateObjectsUsingBlock:(void (^)(id obj, NSUInteger idx, BOOL *stop))block
+{
+    if (!block) return;
+    BOOL stop = NO;
+    for (NSInteger i = 0; i < self.count; i++) {
+        block([self objectAtIndexedSubscript:i],i,&stop);
+        if(stop){
+            break;
+        }
+    }
+}
+
+-(NSUInteger)indexOfObjectPassingTest:(BOOL (^)(id obj, NSUInteger, BOOL *stop))predicate
+{
+    if (!predicate) return NSNotFound;
+    __block BOOL bb;
+    __block NSUInteger index;
+    [self enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+       
+        bb = predicate(obj,idx,stop);
+        if (bb) {
+            index = idx;
+        }
+    }];
+    if (bb) {
+        return index;
+    }
+    return NSNotFound;
+}
+
+@end
+
+@implementation PBArray (PBArrayExtended)
+
+-(PBArray *) filteredArrayUsingPredicate:(NSPredicate *)predicate
+{
+    __block PBAppendableArray *newArray = [[PBAppendableArray alloc] initWithValueType:_valueType];
+    [self enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
+
+        BOOL result = [predicate evaluateWithObject:obj];
+        if (result)
+        {
+            if (PBArrayValueTypeBool == _valueType)
+            {
+                [newArray addBool:[(NSNumber *)obj boolValue]];
+            }
+            else if (PBArrayValueTypeInt32 == _valueType)
+            {
+                [newArray addInt32:(SInt32)[(NSNumber *)obj longValue]];
+            }
+            else if (PBArrayValueTypeInt64 == _valueType)
+            {
+                [newArray addInt64:[(NSNumber *)obj longLongValue]];
+            }
+            else if (PBArrayValueTypeUInt32 == _valueType)
+            {
+                 [newArray addUint32:(UInt32)[(NSNumber *)obj unsignedLongValue]];
+            }
+            else if (PBArrayValueTypeUInt64 == _valueType)
+            {
+                [newArray addUint64:[(NSNumber *)obj unsignedLongLongValue]];
+            }
+            else if (_valueType == PBArrayValueTypeFloat)
+            {
+                 [newArray addFloat:[(NSNumber *)obj floatValue]];
+            }
+            else if (_valueType == PBArrayValueTypeDouble)
+            {
+                 [newArray addDouble:[(NSNumber *)obj doubleValue]];
+            }
+
+            
+        }
+    }];
+    return newArray;
+}
+
+- (id)arrayByAppendingArray:(PBArray *)array
+{
+	PBArrayValueTypeAssert(array.valueType);
+
+	PBArray *result = [[[self class] alloc] initWithCount:_count + array.count valueType:_valueType];
+	if (result)
+	{
+		const size_t elementSize = PBArrayValueTypeSize(_valueType);
+		const size_t originalSize = _count * elementSize;
+
+		memcpy(result->_data, _data, originalSize);
+		memcpy(result->_data + originalSize, array.data, array.count * elementSize);
+	}
+
+	return result;
+}
+
+@end
+
+@implementation PBArray (PBArrayCreation)
+
++ (id)arrayWithValueType:(PBArrayValueType)valueType
+{
+	return [[self alloc] initWithValueType:valueType];
+}
+
++ (id)arrayWithValues:(const void *)values count:(NSUInteger)count valueType:(PBArrayValueType)valueType
+{
+	return [[self alloc] initWithValues:values count:count valueType:valueType];
+}
+
++ (id)arrayWithArray:(NSArray *)array valueType:(PBArrayValueType)valueType
+{
+	return [[self alloc] initWithArray:array valueType:valueType];
+}
+
+- (id)initWithValueType:(PBArrayValueType)valueType
+{
+	return [self initWithCount:0 valueType:valueType];
+}
+
+- (id)initWithValues:(const void *)values count:(NSUInteger)count valueType:(PBArrayValueType)valueType
+{
+	if ((self = [self initWithCount:count valueType:valueType]))
+	{
+		memcpy(_data, values, count * PBArrayValueTypeSize(_valueType));
+	}
+
+	return self;
+}
+
+- (id)initWithArray:(NSArray *)array valueType:(PBArrayValueType)valueType
+{
+	if ((self = [self initWithCount:[array count] valueType:valueType]))
+	{
+		const size_t elementSize = PBArrayValueTypeSize(valueType);
+		size_t offset = 0;
+
+        PBArrayValueSetter setter = PBArrayValueTypeSetter(valueType);
+        for (id object in array)
+        {
+            PBArrayNumberAssert(object);
+            setter((NSNumber *)object, _data + offset);
+            offset += elementSize;
+        }
+
+	}
+
+	return self;
+}
+
+@end
+
+#pragma mark -
+#pragma mark PBAppendableArray
+
+@implementation PBAppendableArray
+
+- (void)ensureAdditionalCapacity:(NSUInteger)additionalSlots
+{
+	const NSUInteger requiredSlots = _count + additionalSlots;
+
+	if (requiredSlots > _capacity)
+	{
+		// If we haven't allocated any capacity yet, simply reserve
+		// enough capacity to cover the required number of slots.
+		if (_capacity == 0)
+		{
+			_capacity = requiredSlots;
+		}
+		else
+		{
+			// Otherwise, continue to double our capacity until we
+			// can accomodate the required number of slots.
+			while (_capacity < requiredSlots)
+			{
+				_capacity *= 2;
+			}
+		}
+
+		const size_t size = _capacity * PBArrayValueTypeSize(_valueType);
+		_data = reallocf(_data, size);
+		PBArrayAllocationAssert(_data, size);
+	}
+}
+
+
+
+- (void)addBool:(BOOL)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeBool);
+	[self ensureAdditionalCapacity:1];
+	*(BOOL *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)addInt32:(SInt32)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeInt32);
+	[self ensureAdditionalCapacity:1];
+	*(SInt32 *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)addUint32:(UInt32)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeUInt32);
+	[self ensureAdditionalCapacity:1];
+	*(UInt32 *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)addEnum:(SInt32)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeInt32);
+	[self ensureAdditionalCapacity:1];
+	*(SInt32 *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)addInt64:(int64_t)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeInt64);
+	[self ensureAdditionalCapacity:1];
+	*(SInt64 *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)addUint64:(uint64_t)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeUInt64);
+	[self ensureAdditionalCapacity:1];
+	*(UInt64 *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)addFloat:(Float32)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeFloat);
+	[self ensureAdditionalCapacity:1];
+	*(Float32 *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)addDouble:(Float64)value
+{
+	PBArrayValueTypeAssert(PBArrayValueTypeDouble);
+	[self ensureAdditionalCapacity:1];
+	*(Float64 *)PBArraySlot(_count) = value;
+	_count++;
+}
+
+- (void)appendArray:(PBArray *)array
+{
+	PBArrayValueTypeAssert(array.valueType);
+	[self ensureAdditionalCapacity:array.count];
+
+	const size_t elementSize = PBArrayValueTypeSize(_valueType);
+	memcpy(_data + (_count * elementSize), array.data, array.count * elementSize);
+	_count += array.count;
+}
+
+- (void)appendValues:(const void *)values count:(UInt32)count
+{
+	[self ensureAdditionalCapacity:count];
+
+	const size_t elementSize = PBArrayValueTypeSize(_valueType);
+	memcpy(_data + (_count * elementSize), values, count * elementSize);
+	_count += count;
+}
+
+@end
diff --git a/src/runtime/Classes/ProtocolBuffers.h b/src/runtime/Classes/ProtocolBuffers.h
new file mode 100755
index 0000000..01c6cc6
--- /dev/null
+++ b/src/runtime/Classes/ProtocolBuffers.h
@@ -0,0 +1,40 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import <Foundation/Foundation.h>
+#import "Bootstrap.h"
+#import "AbstractMessage.h"
+#import "AbstractMessageBuilder.h"
+#import "CodedInputStream.h"
+#import "CodedOutputStream.h"
+#import "ConcreteExtensionField.h"
+#import "ExtendableMessage.h"
+#import "ExtendableMessageBuilder.h"
+#import "ExtensionField.h"
+#import "ExtensionRegistry.h"
+#import "Field.h"
+#import "GeneratedMessage.h"
+#import "GeneratedMessageBuilder.h"
+#import "Message.h"
+#import "MessageBuilder.h"
+#import "MutableExtensionRegistry.h"
+#import "MutableField.h"
+#import "PBArray.h"
+#import "UnknownFieldSet.h"
+#import "UnknownFieldSetBuilder.h"
+#import "Utilities.h"
+#import "WireFormat.h"
diff --git a/src/runtime/Classes/RingBuffer.h b/src/runtime/Classes/RingBuffer.h
new file mode 100755
index 0000000..f543f4a
--- /dev/null
+++ b/src/runtime/Classes/RingBuffer.h
@@ -0,0 +1,21 @@
+#import <Foundation/Foundation.h>
+
+@interface RingBuffer : NSObject {
+	NSMutableData *buffer;
+	SInt32 position;
+	SInt32 tail;
+}
+@property (nonatomic, readonly) UInt32 freeSpace;
+
+- (id)initWithData:(NSMutableData*)data;
+
+// Returns false if there is not enough free space in buffer
+- (BOOL)appendByte:(uint8_t)byte;
+
+// Returns number of bytes written
+- (SInt32)appendData:(const NSData*)value offset:(SInt32)offset length:(SInt32)length;
+
+// Returns number of bytes written
+- (SInt32)flushToOutputStream:(NSOutputStream*)stream;
+
+@end
diff --git a/src/runtime/Classes/RingBuffer.m b/src/runtime/Classes/RingBuffer.m
new file mode 100755
index 0000000..5978c2c
--- /dev/null
+++ b/src/runtime/Classes/RingBuffer.m
@@ -0,0 +1,92 @@
+#import "RingBuffer.h"
+
+@implementation RingBuffer
+
+- (id)initWithData:(NSMutableData*)data {
+  if ((self = [super init])) {
+      buffer = data;
+  }
+	return self;
+}
+
+
+- (UInt32)freeSpace {
+	return (UInt32)(position < tail ? tail - position : (buffer.length - position) + tail) - (tail ? 1 : 0);
+}
+
+
+- (BOOL)appendByte:(uint8_t)byte {
+	if (self.freeSpace < 1) return NO;
+	((uint8_t*)buffer.mutableBytes)[position++] = byte;
+	return YES;
+}
+
+
+- (SInt32)appendData:(const NSData*)value offset:(SInt32)offset length:(SInt32)length {
+	SInt32 totalWritten = 0;
+	const uint8_t *input = value.bytes;
+	uint8_t *data = buffer.mutableBytes;
+	
+	if (position >= tail) {
+		totalWritten = MIN((UInt32)buffer.length - position, length);
+		memcpy(data + position, input + offset, totalWritten);
+		position += totalWritten;
+		if (totalWritten == length) return length;
+		length -= totalWritten;
+		offset += totalWritten;
+	}
+	
+	UInt32 freeSpace = self.freeSpace;
+	if (!freeSpace) return totalWritten;
+	
+	if (position == buffer.length) {
+		position = 0;
+	}
+	
+	// position < tail
+	SInt32 written = MIN(freeSpace, length);
+	memcpy(data + position, input + offset, written);
+	position += written;
+	totalWritten += written;
+	
+	return totalWritten;
+}
+
+
+- (SInt32)flushToOutputStream:(NSOutputStream*)stream {
+	SInt32 totalWritten = 0;
+	const uint8_t *data = buffer.bytes;
+	
+	if (tail > position) {
+		SInt32 written = (SInt32)[stream write:data + tail maxLength:buffer.length - tail];
+        if (written <= 0) return totalWritten;
+        totalWritten += written;
+		tail += written;
+		if (tail == buffer.length) {
+			tail = 0;
+		}
+	}
+
+	if (tail < position) {
+		SInt32 written = (SInt32)[stream write:data + tail maxLength:position - tail];
+		if (written <= 0) return totalWritten;
+		totalWritten += written;
+		tail += written;
+	}
+
+    if (tail == position) {
+        tail = position = 0;
+    }
+
+    if (position == buffer.length && tail > 0) {
+        position = 0;
+    }
+
+    if (tail == buffer.length) {
+        tail = 0;
+    }
+	
+	return totalWritten;
+}
+
+@end
diff --git a/src/runtime/Classes/TextFormat.h b/src/runtime/Classes/TextFormat.h
new file mode 100755
index 0000000..74f6a11
--- /dev/null
+++ b/src/runtime/Classes/TextFormat.h
@@ -0,0 +1,29 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+@interface PBTextFormat : NSObject {
+
+}
+
++ (SInt32) parseInt32:(NSString*) text;
++ (SInt32) parseUInt32:(NSString*) text;
++ (SInt64) parseInt64:(NSString*) text;
++ (SInt64) parseUInt64:(NSString*) text;
+
++ (NSData*) unescapeBytes:(NSString*) input;
+
+@end
diff --git a/src/runtime/Classes/TextFormat.m b/src/runtime/Classes/TextFormat.m
new file mode 100755
index 0000000..4b7ff00
--- /dev/null
+++ b/src/runtime/Classes/TextFormat.m
@@ -0,0 +1,236 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "TextFormat.h"
+
+#import "Utilities.h"
+
+@implementation PBTextFormat
+
+
+BOOL allZeroes(NSString* string) {
+  for (int i = 0; i < string.length; i++) {
+    if ([string characterAtIndex:i] != '0') {
+      return NO;
+    }
+  }
+
+  return YES;
+}
+
+
+/** Is this an octal digit? */
+BOOL isOctal(unichar c) {
+  return '0' <= c && c <= '7';
+}
+
+
+/** Is this an octal digit? */
+BOOL isDecimal(unichar c) {
+  return '0' <= c && c <= '9';
+}
+
+/** Is this a hex digit? */
+BOOL isHex(unichar c) {
+  return
+  isDecimal(c) ||
+  ('a' <= c && c <= 'f') ||
+  ('A' <= c && c <= 'F');
+}
+
+
++ (SInt64) parseInteger:(NSString*) text
+                isSigned:(BOOL) isSigned
+                  isLong:(BOOL) isLong {
+  if (text.length == 0) {
+    @throw [NSException exceptionWithName:@"NumberFormat" reason:@"Number was blank" userInfo:nil];
+  }
+
+  if (isblank([text characterAtIndex:0])) {
+    @throw [NSException exceptionWithName:@"NumberFormat" reason:@"Invalid character" userInfo:nil];
+  }
+
+  if ([text hasPrefix:@"-"]) {
+    if (!isSigned) {
+      @throw [NSException exceptionWithName:@"NumberFormat" reason:@"Number must be positive" userInfo:nil];
+    }
+  }
+
+  // now call into the appropriate conversion utilities.
+ SInt64 result;
+  const char* in_string = text.UTF8String;
+  char* out_string = NULL;
+  errno = 0;
+  if (isLong) {
+    if (isSigned) {
+      result = strtoll(in_string, &out_string, 0);
+    } else {
+      result = convertUInt64ToInt64(strtoull(in_string, &out_string, 0));
+    }
+  } else {
+    if (isSigned) {
+      result = strtol(in_string, &out_string, 0);
+    } else {
+      result = convertUInt32ToInt32((SInt32)strtoul(in_string, &out_string, 0));
+    }
+  }
+
+  // from the man pages:
+  // (Thus, i* tr is not `\0' but **endptr is `\0' on return, the entire
+  // string was valid.)
+  if (*in_string == 0 || *out_string != 0) {
+    @throw [NSException exceptionWithName:@"NumberFormat" reason:@"IllegalNumber" userInfo:nil];
+  }
+
+  if (errno == ERANGE) {
+    @throw [NSException exceptionWithName:@"NumberFormat" reason:@"Number out of range" userInfo:nil];
+  }
+
+  return result;
+}
+
+
+/**
+ * Parse a 32-bit signed integer from the text.  This function recognizes
+ * the prefixes "0x" and "0" to signify hexidecimal and octal numbers,
+ * respectively.
+ */
++ (SInt32) parseInt32:(NSString*) text {
+  return (SInt32)[self parseInteger:text isSigned:YES isLong:NO];
+}
+
+
+/**
+ * Parse a 32-bit unsigned integer from the text.  This function recognizes
+ * the prefixes "0x" and "0" to signify hexidecimal and octal numbers,
+ * respectively.  The result is coerced to a (signed) {@code int} when returned.
+ */
++ (SInt32) parseUInt32:(NSString*) text {
+  return (SInt32)[self parseInteger:text isSigned:NO isLong:NO];
+}
+
+
+/**
+ * Parse a 64-bit signed integer from the text.  This function recognizes
+ * the prefixes "0x" and "0" to signify hexidecimal and octal numbers,
+ * respectively.
+ */
++ (SInt64) parseInt64:(NSString*) text {
+  return [self parseInteger:text isSigned:YES isLong:YES];
+}
+
+
+/**
+ * Parse a 64-bit unsigned integer from the text.  This function recognizes
+ * the prefixes "0x" and "0" to signify hexidecimal and octal numbers,
+ * respectively.  The result is coerced to a (signed) {@code SInt32} when
+ * returned.
+ */
++ (SInt64) parseUInt64:(NSString*) text {
+  return [self parseInteger:text isSigned:NO isLong:YES];
+}
+
+/**
+ * Interpret a character as a digit (in any base up to 36) and return the
+ * numeric value.  This is like {@code Character.digit()} but we don't accept
+ * non-ASCII digits.
+ */
+SInt32 digitValue(unichar c) {
+  if ('0' <= c && c <= '9') {
+    return c - '0';
+  } else if ('a' <= c && c <= 'z') {
+    return c - 'a' + 10;
+  } else {
+    return c - 'A' + 10;
+  }
+}
+
+
+/**
+ * Un-escape a byte sequence as escaped using
+ * {@link #escapeBytes(ByteString)}.  Two-digit hex escapes (starting with
+ * "\x") are also recognized.
+ */
++ (NSData*) unescapeBytes:(NSString*) input {
+  NSMutableData* result = [NSMutableData dataWithLength:input.length];
+
+  SInt32 pos = 0;
+  for (SInt32 i = 0; i < input.length; i++) {
+    unichar c = [input characterAtIndex:i];
+    if (c == '\\') {
+      if (i + 1 < input.length) {
+        ++i;
+        c = [input characterAtIndex:i];
+        if (isOctal(c)) {
+          // Octal escape.
+          SInt32 code = digitValue(c);
+          if (i + 1 < input.length && isOctal([input characterAtIndex:(i + 1)])) {
+            ++i;
+            code = code * 8 + digitValue([input characterAtIndex:i]);
+          }
+          if (i + 1 < input.length && isOctal([input characterAtIndex:(i + 1)])) {
+            ++i;
+            code = code * 8 + digitValue([input characterAtIndex:i]);
+          }
+          ((int8_t*)result.mutableBytes)[pos++] = (int8_t)code;
+        } else {
+          switch (c) {
+            case 'a' : ((int8_t*)result.mutableBytes)[pos++] = 0x07; break;
+            case 'b' : ((int8_t*)result.mutableBytes)[pos++] = '\b'; break;
+            case 'f' : ((int8_t*)result.mutableBytes)[pos++] = '\f'; break;
+            case 'n' : ((int8_t*)result.mutableBytes)[pos++] = '\n'; break;
+            case 'r' : ((int8_t*)result.mutableBytes)[pos++] = '\r'; break;
+            case 't' : ((int8_t*)result.mutableBytes)[pos++] = '\t'; break;
+            case 'v' : ((int8_t*)result.mutableBytes)[pos++] = 0x0b; break;
+            case '\\': ((int8_t*)result.mutableBytes)[pos++] = '\\'; break;
+            case '\'': ((int8_t*)result.mutableBytes)[pos++] = '\''; break;
+            case '"' : ((int8_t*)result.mutableBytes)[pos++] = '\"'; break;
+
+            case 'x': // hex escape
+            {
+              SInt32 code = 0;
+              if (i + 1 < input.length && isHex([input characterAtIndex:(i + 1)])) {
+                ++i;
+                code = digitValue([input characterAtIndex:i]);
+              } else {
+                @throw [NSException exceptionWithName:@"InvalidEscape" reason:@"Invalid escape sequence: '\\x' with no digits" userInfo:nil];
+              }
+              if (i + 1 < input.length && isHex([input characterAtIndex:(i + 1)])) {
+                ++i;
+                code = code * 16 + digitValue([input characterAtIndex:i]);
+              }
+              ((int8_t*)result.mutableBytes)[pos++] = (int8_t)code;
+              break;
+            }
+
+            default:
+              @throw [NSException exceptionWithName:@"InvalidEscape" reason:@"Invalid escape sequence" userInfo:nil];
+          }
+        }
+      } else {
+        @throw [NSException exceptionWithName:@"InvalidEscape" reason:@"Invalid escape sequence: '\\' at end of string" userInfo:nil];
+      }
+    } else {
+      ((int8_t*)result.mutableBytes)[pos++] = (int8_t)c;
+    }
+  }
+
+  [result setLength:pos];
+  return result;
+}
+
+@end
diff --git a/src/runtime/Classes/UnknownFieldSet.h b/src/runtime/Classes/UnknownFieldSet.h
new file mode 100755
index 0000000..922d107
--- /dev/null
+++ b/src/runtime/Classes/UnknownFieldSet.h
@@ -0,0 +1,50 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+@class PBCodedOutputStream;
+@class PBField;
+@class PBUnknownFieldSetBuilder;
+
+@interface PBUnknownFieldSet : NSObject {
+@private
+  NSDictionary* fields;
+}
+
+@property (readonly, strong) NSDictionary* fields;
+
++ (PBUnknownFieldSet*) defaultInstance;
+
++ (PBUnknownFieldSet*) setWithFields:(NSMutableDictionary*) fields;
++ (PBUnknownFieldSet*) parseFromData:(NSData*) data;
+
++ (PBUnknownFieldSetBuilder*) builder;
++ (PBUnknownFieldSetBuilder*) builderWithUnknownFields:(PBUnknownFieldSet*) other;
+
+- (void) writeAsMessageSetTo:(PBCodedOutputStream*) output;
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output;
+- (NSData*) data;
+
+- (SInt32) serializedSize;
+- (SInt32) serializedSizeAsMessageSet;
+
+- (BOOL) hasField:(SInt32) number;
+- (PBField*) getField:(SInt32) number;
+
+- (void) writeDescriptionTo:(NSMutableString*) output
+                 withIndent:(NSString*) indent;
+
+@end
diff --git a/src/runtime/Classes/UnknownFieldSet.m b/src/runtime/Classes/UnknownFieldSet.m
new file mode 100755
index 0000000..4f3a00d
--- /dev/null
+++ b/src/runtime/Classes/UnknownFieldSet.m
@@ -0,0 +1,172 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "UnknownFieldSet.h"
+
+#import "CodedInputStream.h"
+#import "CodedOutputStream.h"
+#import "Field.h"
+#import "UnknownFieldSetBuilder.h"
+
+@interface PBUnknownFieldSet()
+@property (strong) NSDictionary* fields;
+@end
+
+
+@implementation PBUnknownFieldSet
+
+static PBUnknownFieldSet* defaultInstance = nil;
+
++ (void) initialize {
+  if (self == [PBUnknownFieldSet class]) {
+      defaultInstance = [PBUnknownFieldSet setWithFields:[NSMutableDictionary dictionary]];
+  }
+}
+
+
+@synthesize fields;
+
+
+
+
++ (PBUnknownFieldSet*) defaultInstance {
+  return defaultInstance;
+}
+
+
+- (id) initWithFields:(NSMutableDictionary*) fields_ {
+  if ((self = [super init])) {
+    self.fields = fields_;
+  }
+
+  return self;
+}
+
+
++ (PBUnknownFieldSet*) setWithFields:(NSMutableDictionary*) fields {
+    return [[PBUnknownFieldSet alloc] initWithFields:fields];
+}
+
+
+- (BOOL) hasField:(SInt32) number {
+  return [fields objectForKey:@(number)] != nil;
+}
+
+
+- (PBField*) getField:(SInt32) number {
+  PBField* result = [fields objectForKey:@(number)];
+  return (result == nil) ? [PBField defaultInstance] : result;
+}
+
+
+- (void) writeToCodedOutputStream:(PBCodedOutputStream*) output {
+  NSArray* sortedKeys = [fields.allKeys sortedArrayUsingSelector:@selector(compare:)];
+  for (NSNumber* number in sortedKeys) {
+    PBField* value = [fields objectForKey:number];
+    [value writeTo:(SInt32)number.integerValue output:output];
+  }
+}
+
+
+- (void) writeToOutputStream:(NSOutputStream*) output {
+  PBCodedOutputStream* codedOutput = [PBCodedOutputStream streamWithOutputStream:output];
+  [self writeToCodedOutputStream:codedOutput];
+  [codedOutput flush];
+}
+
+
+- (void) writeDescriptionTo:(NSMutableString*) output
+                 withIndent:(NSString *)indent {
+  NSArray* sortedKeys = [fields.allKeys sortedArrayUsingSelector:@selector(compare:)];
+  for (NSNumber* number in sortedKeys) {
+    PBField* value = [fields objectForKey:number];
+    [value writeDescriptionFor:(SInt32)number.integerValue to:output withIndent:indent];
+  }
+}
+
+
++ (PBUnknownFieldSet*) parseFromCodedInputStream:(PBCodedInputStream*) input {
+  return [[[PBUnknownFieldSet builder] mergeFromCodedInputStream:input] build];
+}
+
+
++ (PBUnknownFieldSet*) parseFromData:(NSData*) data {
+  return [[[PBUnknownFieldSet builder] mergeFromData:data] build];
+}
+
+
++ (PBUnknownFieldSet*) parseFromInputStream:(NSInputStream*) input {
+  return [[[PBUnknownFieldSet builder] mergeFromInputStream:input] build];
+}
+
+
++ (PBUnknownFieldSetBuilder*) builder {
+    return [[PBUnknownFieldSetBuilder alloc] init];
+}
+
+
++ (PBUnknownFieldSetBuilder*) builderWithUnknownFields:(PBUnknownFieldSet*) copyFrom {
+  return [[PBUnknownFieldSet builder] mergeUnknownFields:copyFrom];
+}
+
+
+/** Get the number of bytes required to encode this set. */
+- (SInt32) serializedSize {
+  SInt32 result = 0;
+  for (NSNumber* number in fields) {
+    result += [[fields objectForKey:number] getSerializedSize:(SInt32)number.integerValue];
+  }
+  return result;
+}
+
+/**
+ * Serializes the set and writes it to {@code output} using
+ * {@code MessageSet} wire format.
+ */
+- (void) writeAsMessageSetTo:(PBCodedOutputStream*) output {
+  for (NSNumber* number in fields) {
+    [[fields objectForKey:number] writeAsMessageSetExtensionTo:(SInt32)number.integerValue output:output];
+  }
+}
+
+
+/**
+ * Get the number of bytes required to encode this set using
+ * {@code MessageSet} wire format.
+ */
+- (SInt32) serializedSizeAsMessageSet {
+  SInt32 result = 0;
+  for (NSNumber* number in fields) {
+    result += [[fields objectForKey:number] getSerializedSizeAsMessageSetExtension:(SInt32)number.integerValue];
+  }
+  return result;
+}
+
+
+/**
+ * Serializes the message to a {@code ByteString} and returns it. This is
+ * just a trivial wrapper around {@link #writeTo(PBCodedOutputStream)}.
+ */
+- (NSData*) data {
+  NSMutableData* data = [NSMutableData dataWithLength:self.serializedSize];
+  PBCodedOutputStream* output = [PBCodedOutputStream streamWithData:data];
+
+  [self writeToCodedOutputStream:output];
+  return data;
+}
+
+@end
diff --git a/src/runtime/Classes/UnknownFieldSetBuilder.h b/src/runtime/Classes/UnknownFieldSetBuilder.h
new file mode 100755
index 0000000..3b0b080
--- /dev/null
+++ b/src/runtime/Classes/UnknownFieldSetBuilder.h
@@ -0,0 +1,53 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "MessageBuilder.h"
+
+@class PBField;
+@class PBMutableField;
+
+@interface PBUnknownFieldSetBuilder : NSObject <PBMessageBuilder> {
+@private
+  NSMutableDictionary* fields;
+
+  // Optimization:  We keep around a builder for the last field that was
+  //   modified so that we can efficiently add to it multiple times in a
+  //   row (important when parsing an unknown repeated field).
+  SInt32 lastFieldNumber;
+
+  PBMutableField* lastField;
+}
+
++ (PBUnknownFieldSetBuilder*) createBuilder:(PBUnknownFieldSet*) unknownFields;
+
+- (PBUnknownFieldSet*) build;
+- (PBUnknownFieldSetBuilder*) mergeUnknownFields:(PBUnknownFieldSet*) other;
+
+- (PBUnknownFieldSetBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input;
+- (PBUnknownFieldSetBuilder*) mergeFromData:(NSData*) data;
+- (PBUnknownFieldSetBuilder*) mergeFromInputStream:(NSInputStream*) input;
+
+- (PBUnknownFieldSetBuilder*) mergeVarintField:(SInt32) number value:(SInt32) value;
+
+- (BOOL) mergeFieldFrom:(SInt32) tag input:(PBCodedInputStream*) input;
+
+- (PBUnknownFieldSetBuilder*) addField:(PBField*) field forNumber:(SInt32) number;
+
+- (PBUnknownFieldSetBuilder*) clear;
+- (PBUnknownFieldSetBuilder*) mergeField:(PBField*) field forNumber:(SInt32) number;
+
+@end
diff --git a/src/runtime/Classes/UnknownFieldSetBuilder.m b/src/runtime/Classes/UnknownFieldSetBuilder.m
new file mode 100755
index 0000000..0d30c77
--- /dev/null
+++ b/src/runtime/Classes/UnknownFieldSetBuilder.m
@@ -0,0 +1,270 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "UnknownFieldSetBuilder.h"
+
+#import "CodedInputStream.h"
+#import "Field.h"
+#import "MutableField.h"
+#import "UnknownFieldSet.h"
+#import "WireFormat.h"
+
+@interface PBUnknownFieldSetBuilder ()
+@property (strong) NSMutableDictionary* fields;
+@property SInt32 lastFieldNumber;
+@property (strong) PBMutableField* lastField;
+@end
+
+
+@implementation PBUnknownFieldSetBuilder
+
+@synthesize fields;
+@synthesize lastFieldNumber;
+@synthesize lastField;
+
+
+- (id) init {
+  if ((self = [super init])) {
+    self.fields = [NSMutableDictionary dictionary];
+  }
+  return self;
+}
+
+
++ (PBUnknownFieldSetBuilder*) createBuilder:(PBUnknownFieldSet*) unknownFields {
+    PBUnknownFieldSetBuilder* builder = [[PBUnknownFieldSetBuilder alloc] init];
+  [builder mergeUnknownFields:unknownFields];
+  return builder;
+}
+
+
+/**
+ * Add a field to the {@code PBUnknownFieldSet}.  If a field with the same
+ * number already exists, it is removed.
+ */
+- (PBUnknownFieldSetBuilder*) addField:(PBField*) field forNumber:(SInt32) number {
+  if (number == 0) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"" userInfo:nil];
+  }
+  if (lastField != nil && lastFieldNumber == number) {
+    // Discard this.
+    self.lastField = nil;
+    lastFieldNumber = 0;
+  }
+  [fields setObject:field forKey:@(number)];
+  return self;
+}
+
+
+/**
+ * Get a field builder for the given field number which includes any
+ * values that already exist.
+ */
+- (PBMutableField*) getFieldBuilder:(SInt32) number {
+  if (lastField != nil) {
+    if (number == lastFieldNumber) {
+      return lastField;
+    }
+    // Note:  addField() will reset lastField and lastFieldNumber.
+    [self addField:lastField forNumber:lastFieldNumber];
+  }
+  if (number == 0) {
+    return nil;
+  } else {
+    PBField* existing = [fields objectForKey:@(number)];
+    lastFieldNumber = number;
+    self.lastField = [PBMutableField field];
+    if (existing != nil) {
+      [lastField mergeFromField:existing];
+    }
+    return lastField;
+  }
+}
+
+
+- (PBUnknownFieldSet*) build {
+  [self getFieldBuilder:0];  // Force lastField to be built.
+  PBUnknownFieldSet* result;
+  if (fields.count == 0) {
+    result = [PBUnknownFieldSet defaultInstance];
+  } else {
+    result = [PBUnknownFieldSet setWithFields:fields];
+  }
+  self.fields = nil;
+  return result;
+}
+
+- (PBUnknownFieldSet*) buildPartial {
+  @throw [NSException exceptionWithName:@"UnsupportedMethod" reason:@"" userInfo:nil];
+}
+
+- (PBUnknownFieldSet*) clone {
+  @throw [NSException exceptionWithName:@"UnsupportedMethod" reason:@"" userInfo:nil];
+}
+
+- (BOOL) isInitialized {
+  return YES;
+}
+
+- (PBUnknownFieldSet*) defaultInstance {
+  @throw [NSException exceptionWithName:@"UnsupportedMethod" reason:@"" userInfo:nil];
+}
+
+- (PBUnknownFieldSet*) unknownFields {
+  return [self build];
+}
+
+- (id<PBMessageBuilder>) setUnknownFields:(PBUnknownFieldSet*) unknownFields {
+  @throw [NSException exceptionWithName:@"UnsupportedMethod" reason:@"" userInfo:nil];
+}
+
+/** Check if the given field number is present in the set. */
+- (BOOL) hasField:(SInt32) number {
+  if (number == 0) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"" userInfo:nil];
+  }
+
+  return number == lastFieldNumber || ([fields objectForKey:@(number)] != nil);
+}
+
+
+/**
+ * Add a field to the {@code PBUnknownFieldSet}.  If a field with the same
+ * number already exists, the two are merged.
+ */
+- (PBUnknownFieldSetBuilder*) mergeField:(PBField*) field forNumber:(SInt32) number {
+  if (number == 0) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"" userInfo:nil];
+  }
+  if ([self hasField:number]) {
+    [[self getFieldBuilder:number] mergeFromField:field];
+  } else {
+    // Optimization:  We could call getFieldBuilder(number).mergeFrom(field)
+    // in this case, but that would create a copy of the PBField object.
+    // We'd rather reuse the one passed to us, so call addField() instead.
+    [self addField:field forNumber:number];
+  }
+
+  return self;
+}
+
+
+- (PBUnknownFieldSetBuilder*) mergeUnknownFields:(PBUnknownFieldSet*) other {
+  if (other != [PBUnknownFieldSet defaultInstance]) {
+    for (NSNumber* number in other.fields) {
+      PBField* field = [other.fields objectForKey:number];
+      [self mergeField:field forNumber:(SInt32)[number integerValue]];
+    }
+  }
+  return self;
+}
+
+
+- (PBUnknownFieldSetBuilder*) mergeFromData:(NSData*) data {
+  PBCodedInputStream* input = [PBCodedInputStream streamWithData:data];
+  [self mergeFromCodedInputStream:input];
+  [input checkLastTagWas:0];
+  return self;
+}
+
+
+- (PBUnknownFieldSetBuilder*) mergeFromData:(NSData*) data extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  PBCodedInputStream* input = [PBCodedInputStream streamWithData:data];
+  [self mergeFromCodedInputStream:input extensionRegistry:extensionRegistry];
+  [input checkLastTagWas:0];
+  return self;
+}
+
+
+- (PBUnknownFieldSetBuilder*) mergeFromInputStream:(NSInputStream*) input {
+  @throw [NSException exceptionWithName:@"UnsupportedMethod" reason:@"" userInfo:nil];
+}
+
+- (PBUnknownFieldSetBuilder*) mergeFromInputStream:(NSInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  @throw [NSException exceptionWithName:@"UnsupportedMethod" reason:@"" userInfo:nil];
+}
+
+- (PBUnknownFieldSetBuilder*) mergeVarintField:(SInt32) number value:(SInt32) value {
+  if (number == 0) {
+    @throw [NSException exceptionWithName:@"IllegalArgument" reason:@"Zero is not a valid field number." userInfo:nil];
+  }
+
+  [[self getFieldBuilder:number] addVarint:value];
+  return self;
+}
+
+
+/**
+ * Parse a single field from {@code input} and merge it into this set.
+ * @param tag The field's tag number, which was already parsed.
+ * @return {@code NO} if the tag is an engroup tag.
+ */
+- (BOOL) mergeFieldFrom:(SInt32) tag input:(PBCodedInputStream*) input {
+  SInt32 number = PBWireFormatGetTagFieldNumber(tag);
+  switch (PBWireFormatGetTagWireType(tag)) {
+    case PBWireFormatVarint:
+      [[self getFieldBuilder:number] addVarint:[input readInt64]];
+      return YES;
+    case PBWireFormatFixed64:
+      [[self getFieldBuilder:number] addFixed64:[input readFixed64]];
+      return YES;
+    case PBWireFormatLengthDelimited:
+      [[self getFieldBuilder:number] addLengthDelimited:[input readData]];
+      return YES;
+    case PBWireFormatStartGroup: {
+      PBUnknownFieldSetBuilder* subBuilder = [PBUnknownFieldSet builder];
+      [input readUnknownGroup:number builder:subBuilder];
+      [[self getFieldBuilder:number] addGroup:[subBuilder build]];
+      return YES;
+    }
+    case PBWireFormatEndGroup:
+      return NO;
+    case PBWireFormatFixed32:
+      [[self getFieldBuilder:number] addFixed32:[input readFixed32]];
+      return YES;
+    default:
+      @throw [NSException exceptionWithName:@"InvalidProtocolBuffer" reason:@"" userInfo:nil];
+  }
+}
+
+
+/**
+ * Parse an entire message from {@code input} and merge its fields into
+ * this set.
+ */
+- (PBUnknownFieldSetBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input {
+  while (YES) {
+    SInt32 tag = [input readTag];
+    if (tag == 0 || ![self mergeFieldFrom:tag input:input]) {
+      break;
+    }
+  }
+  return self;
+}
+
+- (PBUnknownFieldSetBuilder*) mergeFromCodedInputStream:(PBCodedInputStream*) input extensionRegistry:(PBExtensionRegistry*) extensionRegistry {
+  @throw [NSException exceptionWithName:@"UnsupportedMethod" reason:@"" userInfo:nil];
+}
+
+- (PBUnknownFieldSetBuilder*) clear {
+  self.fields = [NSMutableDictionary dictionary];
+  self.lastFieldNumber = 0;
+  self.lastField = nil;
+  return self;
+}
+
+@end
diff --git a/src/runtime/Classes/Utilities.h b/src/runtime/Classes/Utilities.h
new file mode 100755
index 0000000..96f432a
--- /dev/null
+++ b/src/runtime/Classes/Utilities.h
@@ -0,0 +1,335 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Message.h"
+
+SInt64 convertFloat64ToInt64(Float64 f);
+SInt32 convertFloat32ToInt32(Float32 f);
+Float64 convertInt64ToFloat64(SInt64 f);
+Float32 convertInt32ToFloat32(SInt32 f);
+
+UInt64 convertInt64ToUInt64(SInt64 i);
+SInt64  convertUInt64ToInt64(UInt64 u);
+UInt32 convertInt32ToUInt32(SInt32 i);
+SInt32  convertUInt32ToInt32(UInt32 u);
+
+SInt32 logicalRightShift32(SInt32 value, SInt32 spaces);
+SInt64 logicalRightShift64(SInt64 value, SInt32 spaces);
+
+
+/**
+ * Decode a ZigZag-encoded 32-bit value.  ZigZag encodes signed integers
+ * into values that can be efficiently encoded with varint.  (Otherwise,
+ * negative values must be sign-extended to 64 bits to be varint encoded,
+ * thus always taking 10 bytes on the wire.)
+ *
+ * @param n An unsigned 32-bit integer, stored in a signed int.
+ * @return A signed 32-bit integer.
+ */
+SInt32 decodeZigZag32(SInt32 n);
+
+/**
+ * Decode a ZigZag-encoded 64-bit value.  ZigZag encodes signed integers
+ * into values that can be efficiently encoded with varint.  (Otherwise,
+ * negative values must be sign-extended to 64 bits to be varint encoded,
+ * thus always taking 10 bytes on the wire.)
+ *
+ * @param n An unsigned 64-bit integer, stored in a signed int.
+ * @return A signed 64-bit integer.
+ */
+SInt64 decodeZigZag64(SInt64 n);
+
+
+/**
+ * Encode a ZigZag-encoded 32-bit value.  ZigZag encodes signed integers
+ * into values that can be efficiently encoded with varint.  (Otherwise,
+ * negative values must be sign-extended to 64 bits to be varint encoded,
+ * thus always taking 10 bytes on the wire.)
+ *
+ * @param n A signed 32-bit integer.
+ * @return An unsigned 32-bit integer, stored in a signed int.
+ */
+SInt32 encodeZigZag32(SInt32 n);
+
+/**
+ * Encode a ZigZag-encoded 64-bit value.  ZigZag encodes signed integers
+ * into values that can be efficiently encoded with varint.  (Otherwise,
+ * negative values must be sign-extended to 64 bits to be varint encoded,
+ * thus always taking 10 bytes on the wire.)
+ *
+ * @param n A signed 64-bit integer.
+ * @return An unsigned 64-bit integer, stored in a signed int.
+ */
+SInt64 encodeZigZag64(SInt64 n);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code double} field, including tag.
+ */
+SInt32 computeDoubleSize(SInt32 fieldNumber, Float64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code float} field, including tag.
+ */
+SInt32 computeFloatSize(SInt32 fieldNumber, Float32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code uint64} field, including tag.
+ */
+SInt32 computeUInt64Size(SInt32 fieldNumber, SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code int64} field, including tag.
+ */
+SInt32 computeInt64Size(SInt32 fieldNumber, SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code int32} field, including tag.
+ */
+SInt32 computeInt32Size(SInt32 fieldNumber, SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code fixed64} field, including tag.
+ */
+SInt32 computeFixed64Size(SInt32 fieldNumber, SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code fixed32} field, including tag.
+ */
+SInt32 computeFixed32Size(SInt32 fieldNumber, SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code bool} field, including tag.
+ */
+SInt32 computeBoolSize(SInt32 fieldNumber, BOOL value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code string} field, including tag.
+ */
+SInt32 computeStringSize(SInt32 fieldNumber, const NSString* value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code group} field, including tag.
+ */
+SInt32 computeGroupSize(SInt32 fieldNumber, const id<PBMessage> value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code group} field represented by an {@code PBUnknownFieldSet}, including
+ * tag.
+ */
+SInt32 computeUnknownGroupSize(SInt32 fieldNumber, const PBUnknownFieldSet* value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * embedded message field, including tag.
+ */
+SInt32 computeMessageSize(SInt32 fieldNumber, const id<PBMessage> value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code bytes} field, including tag.
+ */
+SInt32 computeDataSize(SInt32 fieldNumber, const NSData* value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code uint32} field, including tag.
+ */
+SInt32 computeUInt32Size(SInt32 fieldNumber, SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sfixed32} field, including tag.
+ */
+SInt32 computeSFixed32Size(SInt32 fieldNumber, SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sfixed64} field, including tag.
+ */
+SInt32 computeSFixed64Size(SInt32 fieldNumber, SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sint32} field, including tag.
+ */
+SInt32 computeSInt32Size(SInt32 fieldNumber, SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sint64} field, including tag.
+ */
+SInt32 computeSInt64Size(SInt32 fieldNumber, SInt64 value);
+
+/** Compute the number of bytes that would be needed to encode a tag. */
+SInt32 computeTagSize(SInt32 fieldNumber);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code double} field, including tag.
+ */
+SInt32 computeDoubleSizeNoTag(Float64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code float} field, including tag.
+ */
+SInt32 computeFloatSizeNoTag(Float32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code uint64} field, including tag.
+ */
+SInt32 computeUInt64SizeNoTag(SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code int64} field, including tag.
+ */
+SInt32 computeInt64SizeNoTag(SInt64 value);
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code int32} field, including tag.
+ */
+SInt32 computeInt32SizeNoTag(SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code fixed64} field, including tag.
+ */
+SInt32 computeFixed64SizeNoTag(SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code fixed32} field, including tag.
+ */
+SInt32 computeFixed32SizeNoTag(SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code bool} field, including tag.
+ */
+SInt32 computeBoolSizeNoTag(BOOL value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code string} field, including tag.
+ */
+SInt32 computeStringSizeNoTag(const NSString* value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code group} field, including tag.
+ */
+SInt32 computeGroupSizeNoTag(const id<PBMessage> value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code group} field represented by an {@code PBUnknownFieldSet}, including
+ * tag.
+ */
+SInt32 computeUnknownGroupSizeNoTag(const PBUnknownFieldSet* value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * embedded message field, including tag.
+ */
+SInt32 computeMessageSizeNoTag(const id<PBMessage> value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code bytes} field, including tag.
+ */
+SInt32 computeDataSizeNoTag(const NSData* value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * {@code uint32} field, including tag.
+ */
+SInt32 computeUInt32SizeNoTag(SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * enum field, including tag.  Caller is responsible for converting the
+ * enum value to its numeric value.
+ */
+SInt32 computeEnumSizeNoTag(SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sfixed32} field, including tag.
+ */
+SInt32 computeSFixed32SizeNoTag(SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sfixed64} field, including tag.
+ */
+SInt32 computeSFixed64SizeNoTag(SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sint32} field, including tag.
+ */
+SInt32 computeSInt32SizeNoTag(SInt32 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * {@code sint64} field, including tag.
+ */
+SInt32 computeSInt64SizeNoTag(SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a varint.
+ * {@code value} is treated as unsigned, so it won't be sign-extended if
+ * negative.
+ */
+SInt32 computeRawVarint32Size(SInt32 value);
+
+/** Compute the number of bytes that would be needed to encode a varint. */
+SInt32 computeRawVarint64Size(SInt64 value);
+
+/**
+ * Compute the number of bytes that would be needed to encode a
+ * MessageSet extension to the stream.  For historical reasons,
+ * the wire format differs from normal fields.
+ */
+SInt32 computeMessageSetExtensionSize(SInt32 fieldNumber, const id<PBMessage> value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * unparsed MessageSet extension field to the stream.  For
+ * historical reasons, the wire format differs from normal fields.
+ */
+SInt32 computeRawMessageSetExtensionSize(SInt32 fieldNumber, const NSData* value);
+
+/**
+ * Compute the number of bytes that would be needed to encode an
+ * enum field, including tag.  Caller is responsible for converting the
+ * enum value to its numeric value.
+ */
+SInt32 computeEnumSize(SInt32 fieldNumber, SInt32 value);
diff --git a/src/runtime/Classes/Utilities.m b/src/runtime/Classes/Utilities.m
new file mode 100755
index 0000000..a8f951f
--- /dev/null
+++ b/src/runtime/Classes/Utilities.m
@@ -0,0 +1,351 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "Utilities.h"
+
+#import "UnknownFieldSet.h"
+#import "WireFormat.h"
+
+const SInt32 LITTLE_ENDIAN_32_SIZE = 4;
+const SInt32 LITTLE_ENDIAN_64_SIZE = 8;
+
+
+SInt64 convertFloat64ToInt64(Float64 v) {
+  union { Float64 f; SInt64 i; } u;
+  u.f = v;
+  return u.i;
+}
+
+
+SInt32 convertFloat32ToInt32(Float32 v) {
+  union { Float32 f; SInt32 i; } u;
+  u.f = v;
+  return u.i;
+}
+
+
+Float64 convertInt64ToFloat64(SInt64 v) {
+  union { Float64 f; SInt64 i; } u;
+  u.i = v;
+  return u.f;
+}
+
+
+Float32 convertInt32ToFloat32(SInt32 v) {
+  union { Float32 f; SInt32 i; } u;
+  u.i = v;
+  return u.f;
+}
+
+
+UInt64 convertInt64ToUInt64(SInt64 v) {
+  union { SInt64 i; UInt64 u; } u;
+  u.i = v;
+  return u.u;
+}
+
+
+SInt64 convertUInt64ToInt64(UInt64 v) {
+  union { SInt64 i; UInt64 u; } u;
+  u.u = v;
+  return u.i;
+}
+
+UInt32 convertInt32ToUInt32(SInt32 v) {
+  union { SInt32 i; UInt32 u; } u;
+  u.i = v;
+  return u.u;
+}
+
+
+SInt32 convertUInt32ToInt32(UInt32 v) {
+  union { SInt32 i; UInt32 u; } u;
+  u.u = v;
+  return u.i;
+}
+
+
+SInt32 logicalRightShift32(SInt32 value, SInt32 spaces) {
+  return convertUInt32ToInt32((convertInt32ToUInt32(value) >> spaces));
+}
+
+
+SInt64 logicalRightShift64(SInt64 value, SInt32 spaces) {
+  return convertUInt64ToInt64((convertInt64ToUInt64(value) >> spaces));
+}
+
+
+SInt32 decodeZigZag32(SInt32 n) {
+	return logicalRightShift32(n, 1) ^ -(n & 1);
+}
+
+
+SInt64 decodeZigZag64(SInt64 n) {
+	return logicalRightShift64(n, 1) ^ -(n & 1);
+}
+
+
+SInt32 encodeZigZag32(SInt32 n) {
+	// Note:  the right-shift must be arithmetic
+	return (n << 1) ^ (n >> 31);
+}
+
+
+SInt64 encodeZigZag64(SInt64 n) {
+	// Note:  the right-shift must be arithmetic
+	return (n << 1) ^ (n >> 63);
+}
+
+
+SInt32 computeDoubleSizeNoTag(Float64 value) {
+	return LITTLE_ENDIAN_64_SIZE;
+}
+
+
+SInt32 computeFloatSizeNoTag(Float32 value) {
+	return LITTLE_ENDIAN_32_SIZE;
+}
+
+
+SInt32 computeUInt64SizeNoTag(SInt64 value) {
+	return computeRawVarint64Size(value);
+}
+
+
+SInt32 computeInt64SizeNoTag(SInt64 value) {
+	return computeRawVarint64Size(value);
+}
+
+
+SInt32 computeInt32SizeNoTag(SInt32 value) {
+	if (value >= 0) {
+		return computeRawVarint32Size(value);
+	} else {
+		// Must sign-extend.
+		return 10;
+	}
+}
+
+
+SInt32 computeFixed64SizeNoTag(SInt64 value) {
+	return LITTLE_ENDIAN_64_SIZE;
+}
+
+
+SInt32 computeFixed32SizeNoTag(SInt32 value) {
+	return LITTLE_ENDIAN_32_SIZE;
+}
+
+
+SInt32 computeBoolSizeNoTag(BOOL value) {
+	return 1;
+}
+
+
+SInt32 computeStringSizeNoTag(const NSString* value) {
+	const UInt32 length = (UInt32)[value lengthOfBytesUsingEncoding:NSUTF8StringEncoding];
+	return computeRawVarint32Size(length) + length;
+}
+
+
+SInt32 computeGroupSizeNoTag(const id<PBMessage> value) {
+	return [value serializedSize];
+}
+
+
+SInt32 computeUnknownGroupSizeNoTag(const PBUnknownFieldSet* value) {
+	return value.serializedSize;
+}
+
+
+SInt32 computeMessageSizeNoTag(const id<PBMessage> value) {
+	SInt32 size = [value serializedSize];
+	return computeRawVarint32Size(size) + size;
+}
+
+
+SInt32 computeDataSizeNoTag(const NSData* value) {
+	return computeRawVarint32Size((UInt32)value.length) + (UInt32)value.length;
+}
+
+
+SInt32 computeUInt32SizeNoTag(SInt32 value) {
+	return computeRawVarint32Size(value);
+}
+
+
+SInt32 computeEnumSizeNoTag(SInt32 value) {
+	return computeRawVarint32Size(value);
+}
+
+
+SInt32 computeSFixed32SizeNoTag(SInt32 value) {
+	return LITTLE_ENDIAN_32_SIZE;
+}
+
+
+SInt32 computeSFixed64SizeNoTag(SInt64 value) {
+	return LITTLE_ENDIAN_64_SIZE;
+}
+
+
+SInt32 computeSInt32SizeNoTag(SInt32 value) {
+	return computeRawVarint32Size(encodeZigZag32(value));
+}
+
+
+SInt32 computeSInt64SizeNoTag(SInt64 value) {
+	return computeRawVarint64Size(encodeZigZag64(value));
+}
+
+
+SInt32 computeDoubleSize(SInt32 fieldNumber, Float64 value) {
+	return computeTagSize(fieldNumber) + computeDoubleSizeNoTag(value);
+}
+
+
+SInt32 computeFloatSize(SInt32 fieldNumber, Float32 value) {
+	return computeTagSize(fieldNumber) + computeFloatSizeNoTag(value);
+}
+
+
+SInt32 computeUInt64Size(SInt32 fieldNumber, SInt64 value) {
+	return computeTagSize(fieldNumber) + computeUInt64SizeNoTag(value);
+}
+
+
+SInt32 computeInt64Size(SInt32 fieldNumber, SInt64 value) {
+	return computeTagSize(fieldNumber) + computeInt64SizeNoTag(value);
+}
+
+
+SInt32 computeInt32Size(SInt32 fieldNumber, SInt32 value) {
+	return computeTagSize(fieldNumber) + computeInt32SizeNoTag(value);
+}
+
+
+SInt32 computeFixed64Size(SInt32 fieldNumber, SInt64 value) {
+	return computeTagSize(fieldNumber) + computeFixed64SizeNoTag(value);
+}
+
+
+SInt32 computeFixed32Size(SInt32 fieldNumber, SInt32 value) {
+	return computeTagSize(fieldNumber) + computeFixed32SizeNoTag(value);
+}
+
+
+SInt32 computeBoolSize(SInt32 fieldNumber, BOOL value) {
+	return computeTagSize(fieldNumber) + computeBoolSizeNoTag(value);
+}
+
+
+SInt32 computeStringSize(SInt32 fieldNumber, const NSString* value) {
+	return computeTagSize(fieldNumber) + computeStringSizeNoTag(value);
+}
+
+
+SInt32 computeGroupSize(SInt32 fieldNumber, const id<PBMessage> value) {
+	return computeTagSize(fieldNumber) * 2 + computeGroupSizeNoTag(value);
+}
+
+
+SInt32 computeUnknownGroupSize(SInt32 fieldNumber, const PBUnknownFieldSet* value) {
+	return computeTagSize(fieldNumber) * 2 + computeUnknownGroupSizeNoTag(value);
+}
+
+
+SInt32 computeMessageSize(SInt32 fieldNumber, const id<PBMessage> value) {
+	return computeTagSize(fieldNumber) + computeMessageSizeNoTag(value);
+}
+
+
+SInt32 computeDataSize(SInt32 fieldNumber, const NSData* value) {
+	return computeTagSize(fieldNumber) + computeDataSizeNoTag(value);
+}
+
+
+SInt32 computeUInt32Size(SInt32 fieldNumber, SInt32 value) {
+	return computeTagSize(fieldNumber) + computeUInt32SizeNoTag(value);
+}
+
+
+SInt32 computeEnumSize(SInt32 fieldNumber, SInt32 value) {
+	return computeTagSize(fieldNumber) + computeEnumSizeNoTag(value);
+}
+
+
+SInt32 computeSFixed32Size(SInt32 fieldNumber, SInt32 value) {
+	return computeTagSize(fieldNumber) + computeSFixed32SizeNoTag(value);
+}
+
+
+SInt32 computeSFixed64Size(SInt32 fieldNumber, SInt64 value) {
+	return computeTagSize(fieldNumber) + computeSFixed64SizeNoTag(value);
+}
+
+
+SInt32 computeSInt32Size(SInt32 fieldNumber, SInt32 value) {
+	return computeTagSize(fieldNumber) + computeSInt32SizeNoTag(value);
+}
+
+
+SInt32 computeTagSize(SInt32 fieldNumber) {
+	return computeRawVarint32Size(PBWireFormatMakeTag(fieldNumber, 0));
+}
+
+
+SInt32 computeSInt64Size(SInt32 fieldNumber, SInt64 value) {
+	return computeTagSize(fieldNumber) +
+	computeRawVarint64Size(encodeZigZag64(value));
+}
+
+
+SInt32 computeRawVarint32Size(SInt32 value) {
+	if ((value & (0xffffffff <<  7)) == 0) return 1;
+	if ((value & (0xffffffff << 14)) == 0) return 2;
+	if ((value & (0xffffffff << 21)) == 0) return 3;
+	if ((value & (0xffffffff << 28)) == 0) return 4;
+	return 5;
+}
+
+
+SInt32 computeRawVarint64Size(SInt64 value) {
+	if ((value & (0xffffffffffffffffL <<  7)) == 0) return 1;
+	if ((value & (0xffffffffffffffffL << 14)) == 0) return 2;
+	if ((value & (0xffffffffffffffffL << 21)) == 0) return 3;
+	if ((value & (0xffffffffffffffffL << 28)) == 0) return 4;
+	if ((value & (0xffffffffffffffffL << 35)) == 0) return 5;
+	if ((value & (0xffffffffffffffffL << 42)) == 0) return 6;
+	if ((value & (0xffffffffffffffffL << 49)) == 0) return 7;
+	if ((value & (0xffffffffffffffffL << 56)) == 0) return 8;
+	if ((value & (0xffffffffffffffffL << 63)) == 0) return 9;
+	return 10;
+}
+
+
+SInt32 computeMessageSetExtensionSize(SInt32 fieldNumber, const id<PBMessage> value) {
+	return computeTagSize(PBWireFormatMessageSetItem) * 2 +
+	computeUInt32Size(PBWireFormatMessageSetTypeId, fieldNumber) +
+	computeMessageSize(PBWireFormatMessageSetMessage, value);
+}
+
+
+SInt32 computeRawMessageSetExtensionSize(SInt32 fieldNumber, const NSData* value) {
+	return computeTagSize(PBWireFormatMessageSetItem) * 2 +
+	computeUInt32Size(PBWireFormatMessageSetTypeId, fieldNumber) +
+	computeDataSize(PBWireFormatMessageSetMessage, value);
+}
diff --git a/src/runtime/Classes/WireFormat.h b/src/runtime/Classes/WireFormat.h
new file mode 100755
index 0000000..a075361
--- /dev/null
+++ b/src/runtime/Classes/WireFormat.h
@@ -0,0 +1,41 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+typedef enum {
+  PBWireFormatVarint = 0,
+  PBWireFormatFixed64 = 1,
+  PBWireFormatLengthDelimited = 2,
+  PBWireFormatStartGroup = 3,
+  PBWireFormatEndGroup = 4,
+  PBWireFormatFixed32 = 5,
+
+  PBWireFormatTagTypeBits = 3,
+  PBWireFormatTagTypeMask = 7 /* = (1 << PBWireFormatTagTypeBits) - 1*/,
+
+  PBWireFormatMessageSetItem = 1,
+  PBWireFormatMessageSetTypeId = 2,
+  PBWireFormatMessageSetMessage = 3
+} PBWireFormat;
+
+SInt32 PBWireFormatMakeTag(SInt32 fieldNumber, SInt32 wireType);
+SInt32 PBWireFormatGetTagWireType(SInt32 tag);
+SInt32 PBWireFormatGetTagFieldNumber(SInt32 tag);
+
+#define PBWireFormatMessageSetItemTag (PBWireFormatMakeTag(PBWireFormatMessageSetItem, PBWireFormatStartGroup))
+#define PBWireFormatMessageSetItemEndTag (PBWireFormatMakeTag(PBWireFormatMessageSetItem, PBWireFormatEndGroup))
+#define PBWireFormatMessageSetTypeIdTag (PBWireFormatMakeTag(PBWireFormatMessageSetTypeId, PBWireFormatVarint))
+#define PBWireFormatMessageSetMessageTag (PBWireFormatMakeTag(PBWireFormatMessageSetMessage, PBWireFormatLengthDelimited))
diff --git a/src/runtime/Classes/WireFormat.m b/src/runtime/Classes/WireFormat.m
new file mode 100755
index 0000000..6152f0f
--- /dev/null
+++ b/src/runtime/Classes/WireFormat.m
@@ -0,0 +1,34 @@
+// Protocol Buffers for Objective C
+//
+// Copyright 2010 Booyah Inc.
+// Copyright 2008 Cyrus Najmabadi
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+#import "WireFormat.h"
+
+#import "Utilities.h"
+
+SInt32 PBWireFormatMakeTag(SInt32 fieldNumber, SInt32 wireType) {
+  return (fieldNumber << PBWireFormatTagTypeBits) | wireType;
+}
+
+
+SInt32 PBWireFormatGetTagWireType(SInt32 tag) {
+  return tag & PBWireFormatTagTypeMask;
+}
+
+
+SInt32 PBWireFormatGetTagFieldNumber(SInt32 tag) {
+  return logicalRightShift32(tag, PBWireFormatTagTypeBits);
+}
diff --git a/src/runtime/ProtocolBuffers_Prefix.pch b/src/runtime/ProtocolBuffers_Prefix.pch
new file mode 100755
index 0000000..12c0628
--- /dev/null
+++ b/src/runtime/ProtocolBuffers_Prefix.pch
@@ -0,0 +1,8 @@
+//
+// Prefix header for all source files of the 'CocoaTouchStaticLibrary' target in the 'CocoaTouchStaticLibrary' project.
+//
+
+#ifdef __OBJC__
+    #import <Foundation/Foundation.h>
+	#import "Bootstrap.h"
+#endif