Merge pull request #3791 from mmastrac/master

Avoid unsafe when sizing types
diff --git a/.gitignore b/.gitignore
index c14aad9..9dfabef 100755
--- a/.gitignore
+++ b/.gitignore
@@ -40,6 +40,8 @@
 flatsamplebinary.exe
 flatsampletext
 flatsampletext.exe
+grpctest
+grpctest.exe
 snapshot.sh
 tests/go_gen
 tests/monsterdata_java_wire.mon
@@ -62,3 +64,5 @@
 build/VS2010/FlatBuffers.sdf
 build/VS2010/FlatBuffers.opensdf
 build/VS2010/ipch/**/*.ipch
+*.so
+Testing/Temporary
diff --git a/CMake/PackageDebian.cmake b/CMake/PackageDebian.cmake
new file mode 100644
index 0000000..ebe8931
--- /dev/null
+++ b/CMake/PackageDebian.cmake
@@ -0,0 +1,57 @@
+# ------------------- Debianization ---------------------
+if (UNIX)
+
+    # Set build environment
+    SET(CPACK_GENERATOR "TGZ;DEB")
+    SET(CPACK_SOURCE_TGZ "ON")
+
+    # Common package information
+    SET(CPACK_PACKAGE_DESCRIPTION_SUMMARY
+        "FlatBuffers is an efficient cross platform serialization library for C++, with support for Java, C# and Go. It was created at Google specifically for game development and other performance-critical applications.")
+    SET(CPACK_DEBIAN_PACKAGE_HOMEPAGE "https://github.com/google/flatbuffers")
+    SET(CPACK_DEBIAN_PACKAGE_MAINTAINER "Vitaly Isaev <vitalyisaev2@gmail.com>")
+
+    # Derive package version from git
+    EXECUTE_PROCESS(
+        COMMAND date +%Y%m%d
+        OUTPUT_VARIABLE DATE
+        OUTPUT_STRIP_TRAILING_WHITESPACE
+    )
+    EXECUTE_PROCESS(
+      COMMAND git describe
+      WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
+      OUTPUT_VARIABLE GIT_DESCRIBE_DIRTY
+      OUTPUT_STRIP_TRAILING_WHITESPACE
+    )
+    string(REGEX REPLACE "^v([0-9]+)\\..*" "\\1" VERSION_MAJOR "${GIT_DESCRIBE_DIRTY}")
+    string(REGEX REPLACE "^v[0-9]+\\.([0-9]+).*" "\\1" VERSION_MINOR "${GIT_DESCRIBE_DIRTY}")
+    string(REGEX REPLACE "^v[0-9]+\\.[0-9]+\\.([0-9]+).*" "\\1" VERSION_PATCH "${GIT_DESCRIBE_DIRTY}")
+    string(REGEX REPLACE "^v[0-9]+\\.[0-9]+\\.[0-9]+\\-([0-9]+).*" "\\1" VERSION_COMMIT "${GIT_DESCRIBE_DIRTY}")
+    SET(CPACK_PACKAGE_VERSION_MAJOR ${VERSION_MAJOR})
+    SET(CPACK_PACKAGE_VERSION_MINOR ${VERSION_MINOR})
+    SET(CPACK_PACKAGE_VERSION_PATCH ${VERSION_PATCH})
+    SET(CPACK_PACKAGE_VERSION "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}-${VERSION_COMMIT}")
+    SET(CPACK_DEBIAN_PACKAGE_VERSION "${CPACK_PACKAGE_VERSION}")
+
+    # Derive architecture
+    IF(NOT CPACK_DEBIAN_PACKAGE_ARCHITECTURE)
+      FIND_PROGRAM(DPKG_CMD dpkg)
+      IF(NOT DPKG_CMD)
+        MESSAGE(STATUS "Can not find dpkg in your path, default to i386.")
+        SET(CPACK_DEBIAN_PACKAGE_ARCHITECTURE i386)
+      ENDIF(NOT DPKG_CMD)
+      EXECUTE_PROCESS(COMMAND "${DPKG_CMD}" --print-architecture
+        OUTPUT_VARIABLE CPACK_DEBIAN_PACKAGE_ARCHITECTURE
+        OUTPUT_STRIP_TRAILING_WHITESPACE
+        )
+    ENDIF(NOT CPACK_DEBIAN_PACKAGE_ARCHITECTURE)
+
+    # Package name
+    SET(CPACK_DEBIAN_PACKAGE_NAME "flatbuffers")
+    SET(CPACK_RESOURCE_FILE_LICENSE ${CMAKE_SOURCE_DIR}/LICENSE.txt)
+    SET(CPACK_PACKAGE_FILE_NAME 
+        "${CPACK_DEBIAN_PACKAGE_NAME}_${CPACK_DEBIAN_PACKAGE_VERSION}_${CPACK_DEBIAN_PACKAGE_ARCHITECTURE}")
+
+endif(UNIX)
+
+INCLUDE(CPack)
diff --git a/CMakeLists.txt b/CMakeLists.txt
index c2dd950..7a6b370 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -6,10 +6,15 @@
 option(FLATBUFFERS_CODE_COVERAGE "Enable the code coverage build option." OFF)
 option(FLATBUFFERS_BUILD_TESTS "Enable the build of tests and samples." ON)
 option(FLATBUFFERS_INSTALL "Enable the installation of targets." ON)
-option(FLATBUFFERS_BUILD_FLATLIB "Enable the build of the flatbuffers library" ON)
-option(FLATBUFFERS_BUILD_FLATC "Enable the build of the flatbuffers compiler" ON)
+option(FLATBUFFERS_BUILD_FLATLIB "Enable the build of the flatbuffers library"
+       ON)
+option(FLATBUFFERS_BUILD_FLATC "Enable the build of the flatbuffers compiler"
+       ON)
 option(FLATBUFFERS_BUILD_FLATHASH "Enable the build of flathash" ON)
 option(FLATBUFFERS_BUILD_GRPCTEST "Enable the build of grpctest" OFF)
+option(FLATBUFFERS_BUILD_SHAREDLIB
+       "Enable the build of the flatbuffers shared library"
+       OFF)
 
 if(NOT FLATBUFFERS_BUILD_FLATC AND FLATBUFFERS_BUILD_TESTS)
     message(WARNING
@@ -42,8 +47,11 @@
   src/idl_gen_fbs.cpp
   src/idl_gen_grpc.cpp
   src/flatc.cpp
+  grpc/src/compiler/schema_interface.h
   grpc/src/compiler/cpp_generator.h
   grpc/src/compiler/cpp_generator.cc
+  grpc/src/compiler/go_generator.h
+  grpc/src/compiler/go_generator.cc
 )
 
 set(FlatHash_SRCS
@@ -93,9 +101,12 @@
 # source_group(Compiler FILES ${FlatBuffers_Compiler_SRCS})
 # source_group(Tests FILES ${FlatBuffers_Tests_SRCS})
 
-if(APPLE)
-  set(CMAKE_CXX_FLAGS
-    "${CMAKE_CXX_FLAGS} -std=c++11 -stdlib=libc++ -Wall -pedantic -Werror -Wextra")
+if(EXISTS "${CMAKE_TOOLCHAIN_FILE}")
+  # do not apply any global settings if the toolchain
+  # is being configured externally
+elseif(APPLE)
+  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11 -stdlib=libc++")
+  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -pedantic -Werror -Wextra")
 elseif(CMAKE_COMPILER_IS_GNUCXX)
   if(CYGWIN)
     set(CMAKE_CXX_FLAGS
@@ -108,7 +119,8 @@
     "${CMAKE_CXX_FLAGS} -Wall -pedantic -Werror -Wextra -Werror=shadow")
   if (GCC_VERSION VERSION_GREATER 4.4)
     set(CMAKE_CXX_FLAGS
-      "${CMAKE_CXX_FLAGS} -Wunused-result -Werror=unused-result")
+      "${CMAKE_CXX_FLAGS} -Wunused-result -Werror=unused-result \
+                          -Wunused-parameter -Werror=unused-parameter")
   endif()
 
   # Certain platforms such as ARM do not use signed chars by default
@@ -116,9 +128,10 @@
   set(CMAKE_CXX_FLAGS
     "${CMAKE_CXX_FLAGS} -fsigned-char")
 
-elseif("${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang")
+elseif(${CMAKE_CXX_COMPILER_ID} MATCHES "Clang")
   set(CMAKE_CXX_FLAGS
-      "${CMAKE_CXX_FLAGS} -std=c++0x -stdlib=libc++ -Wall -pedantic -Werror -Wextra")
+      "${CMAKE_CXX_FLAGS} -std=c++0x -stdlib=libc++ -Wall -pedantic -Werror \
+                          -Wextra")
   if(NOT "${CMAKE_SYSTEM_NAME}" MATCHES "FreeBSD")
     set(CMAKE_EXE_LINKER_FLAGS
         "${CMAKE_EXE_LINKER_FLAGS} -lc++abi")
@@ -160,12 +173,19 @@
   add_executable(flathash ${FlatHash_SRCS})
 endif()
 
+if(FLATBUFFERS_BUILD_SHAREDLIB)
+  add_library(flatbuffers_shared SHARED ${FlatBuffers_Library_SRCS})
+  set_target_properties(flatbuffers_shared PROPERTIES OUTPUT_NAME flatbuffers)
+endif()
+
 function(compile_flatbuffers_schema_to_cpp SRC_FBS)
   get_filename_component(SRC_FBS_DIR ${SRC_FBS} PATH)
   string(REGEX REPLACE "\\.fbs$" "_generated.h" GEN_HEADER ${SRC_FBS})
   add_custom_command(
     OUTPUT ${GEN_HEADER}
-    COMMAND "${FLATBUFFERS_FLATC_EXECUTABLE}" -c --no-includes --gen-mutable -o "${SRC_FBS_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}/${SRC_FBS}"
+    COMMAND "${FLATBUFFERS_FLATC_EXECUTABLE}" -c --no-includes --gen-mutable
+            --gen-object-api -o "${SRC_FBS_DIR}"
+            "${CMAKE_CURRENT_SOURCE_DIR}/${SRC_FBS}"
     DEPENDS flatc)
 endfunction()
 
@@ -174,7 +194,8 @@
   string(REGEX REPLACE "\\.fbs$" ".bfbs" GEN_BINARY_SCHEMA ${SRC_FBS})
   add_custom_command(
     OUTPUT ${GEN_BINARY_SCHEMA}
-    COMMAND "${FLATBUFFERS_FLATC_EXECUTABLE}" -b --schema -o "${SRC_FBS_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}/${SRC_FBS}"
+    COMMAND "${FLATBUFFERS_FLATC_EXECUTABLE}" -b --schema -o "${SRC_FBS_DIR}"
+            "${CMAKE_CURRENT_SOURCE_DIR}/${SRC_FBS}"
     DEPENDS flatc)
 endfunction()
 
@@ -205,6 +226,9 @@
   if(FLATBUFFERS_BUILD_FLATC)
     install(TARGETS flatc DESTINATION bin)
   endif()
+  if(FLATBUFFERS_BUILD_SHAREDLIB)
+    install(TARGETS flatbuffers_shared DESTINATION lib)
+  endif()
 endif()
 
 if(FLATBUFFERS_BUILD_TESTS)
@@ -216,3 +240,7 @@
 endif()
 
 include(CMake/BuildFlatBuffers.cmake)
+
+if(FLATBUFFERS_PACKAGE_DEBIAN)
+    include(CMake/PackageDebian.cmake)
+endif()
diff --git a/appveyor.yml b/appveyor.yml
new file mode 100644
index 0000000..63fc12d
--- /dev/null
+++ b/appveyor.yml
@@ -0,0 +1,26 @@
+branches:
+  only:
+    - master
+
+os: Visual Studio 2015
+
+platform:
+  - x86
+  - x64
+
+configuration:
+  - Debug
+  - Release
+
+before_build:
+  - cmake -G"Visual Studio 10 2010"
+
+build:
+  project: ALL_BUILD.vcxproj
+
+#test_script:
+#  - Debug/flattests.exe
+
+#artifacts:
+#  - path: Release/flatc.exe
+#    name: flatc.exe
diff --git a/build_ide/VS2010/FlatBuffers.sln b/build_ide/VS2010/FlatBuffers.sln
deleted file mode 100755
index ac03fdf..0000000
--- a/build_ide/VS2010/FlatBuffers.sln
+++ /dev/null
@@ -1,55 +0,0 @@
-Microsoft Visual Studio Solution File, Format Version 11.00
-# Visual Studio 2010
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flatc", "flatc.vcxproj", "{5B5857E1-64E2-4CED-A12E-45E1B3880496}"
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flatsamplebinary", "flatsamplebinary.vcxproj", "{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}"
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flatsampletext", "flatsampletext.vcxproj", "{F0A15675-1017-4217-BB5B-3372F2C636AB}"
-EndProject
-Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "flattests", "flattests.vcxproj", "{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}"
-EndProject
-Global
-	GlobalSection(SolutionConfigurationPlatforms) = preSolution
-		Debug|Win32 = Debug|Win32
-		Debug|x64 = Debug|x64
-		Release|Win32 = Release|Win32
-		Release|x64 = Release|x64
-	EndGlobalSection
-	GlobalSection(ProjectConfigurationPlatforms) = postSolution
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Debug|Win32.ActiveCfg = Debug|Win32
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Debug|Win32.Build.0 = Debug|Win32
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Debug|x64.ActiveCfg = Debug|x64
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Debug|x64.Build.0 = Debug|x64
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Release|Win32.ActiveCfg = Release|Win32
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Release|Win32.Build.0 = Release|Win32
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Release|x64.ActiveCfg = Release|x64
-		{5B5857E1-64E2-4CED-A12E-45E1B3880496}.Release|x64.Build.0 = Release|x64
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Debug|Win32.ActiveCfg = Debug|Win32
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Debug|Win32.Build.0 = Debug|Win32
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Debug|x64.ActiveCfg = Debug|x64
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Debug|x64.Build.0 = Debug|x64
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Release|Win32.ActiveCfg = Release|Win32
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Release|Win32.Build.0 = Release|Win32
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Release|x64.ActiveCfg = Release|x64
-		{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}.Release|x64.Build.0 = Release|x64
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Debug|Win32.ActiveCfg = Debug|Win32
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Debug|Win32.Build.0 = Debug|Win32
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Debug|x64.ActiveCfg = Debug|x64
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Debug|x64.Build.0 = Debug|x64
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Release|Win32.ActiveCfg = Release|Win32
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Release|Win32.Build.0 = Release|Win32
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Release|x64.ActiveCfg = Release|x64
-		{F0A15675-1017-4217-BB5B-3372F2C636AB}.Release|x64.Build.0 = Release|x64
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Debug|Win32.ActiveCfg = Debug|Win32
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Debug|Win32.Build.0 = Debug|Win32
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Debug|x64.ActiveCfg = Debug|x64
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Debug|x64.Build.0 = Debug|x64
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Release|Win32.ActiveCfg = Release|Win32
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Release|Win32.Build.0 = Release|Win32
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Release|x64.ActiveCfg = Release|x64
-		{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}.Release|x64.Build.0 = Release|x64
-	EndGlobalSection
-	GlobalSection(SolutionProperties) = preSolution
-		HideSolutionNode = FALSE
-	EndGlobalSection
-EndGlobal
diff --git a/build_ide/VS2010/flatc.vcxproj b/build_ide/VS2010/flatc.vcxproj
deleted file mode 100755
index 31cd013..0000000
--- a/build_ide/VS2010/flatc.vcxproj
+++ /dev/null
@@ -1,286 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <ItemGroup Label="ProjectConfigurations">
-    <ProjectConfiguration Include="Debug|Win32">
-      <Configuration>Debug</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Debug|x64">
-      <Configuration>Debug</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|Win32">
-      <Configuration>Release</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|x64">
-      <Configuration>Release</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-  </ItemGroup>
-  <PropertyGroup Label="Globals">
-    <ProjectGUID>{5B5857E1-64E2-4CED-A12E-45E1B3880496}</ProjectGUID>
-    <Keyword>Win32Proj</Keyword>
-    <Platform>Win32</Platform>
-    <ProjectName>flatc</ProjectName>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
-  <ImportGroup Label="ExtensionSettings">
-  </ImportGroup>
-  <ImportGroup Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
-  </ImportGroup>
-  <PropertyGroup Label="UserMacros" />
-  <PropertyGroup>
-    <_ProjectFileVersion>10.0.20506.1</_ProjectFileVersion>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flatc.dir\Debug\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flatc.dir\Debug\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flatc</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flatc</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</GenerateManifest>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flatc.dir\Release\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flatc.dir\Release\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flatc</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flatc</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</GenerateManifest>
-  </PropertyGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flatc.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 /debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flatc.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flatc.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flatc.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions>/debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flatc.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flatc.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flatc.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flatc.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flatc.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flatc.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flatc.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flatc.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemGroup>
-    <ClCompile Include="..\..\src\util.cpp" />
-    <ClInclude Include="..\..\include\flatbuffers\flatbuffers.h" />
-    <ClInclude Include="..\..\include\flatbuffers\idl.h" />
-    <ClInclude Include="..\..\include\flatbuffers\util.h" />
-    <ClCompile Include="..\..\src\idl_gen_fbs.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_general.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_go.cpp">
-      <WarningLevel Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Level4</WarningLevel>
-    </ClCompile>
-    <ClCompile Include="..\..\src\idl_gen_js.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_php.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_python.cpp" />
-    <ClCompile Include="..\..\src\idl_parser.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_cpp.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_text.cpp" />
-    <ClCompile Include="..\..\src\flatc.cpp" />
-  </ItemGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
-  <ImportGroup Label="ExtensionTargets">
-  </ImportGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/VS2010/flatc.vcxproj.user b/build_ide/VS2010/flatc.vcxproj.user
deleted file mode 100755
index 5ef05f7..0000000
--- a/build_ide/VS2010/flatc.vcxproj.user
+++ /dev/null
@@ -1,27 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <LocalDebuggerWorkingDirectory>..\..\tests</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-    <LocalDebuggerCommandArguments>-j -c -n -g --php --no-includes --gen-mutable monster_test.fbs</LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-    <LocalDebuggerCommandArguments>-j -c -n -g -b -t monster_test.fbs monsterdata_test.golden</LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <LocalDebuggerCommandArguments>-j -c -g -n -b -t monster_test.fbs monsterdata_test.golden</LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <LocalDebuggerWorkingDirectory>..\..\tests</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <LocalDebuggerCommandArguments>-j -c -g -b -t monster_test.fbs monsterdata_test.json</LocalDebuggerCommandArguments>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <LocalDebuggerWorkingDirectory>..\..\tests</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/VS2010/flatsamplebinary.vcxproj b/build_ide/VS2010/flatsamplebinary.vcxproj
deleted file mode 100755
index 9d5fb10..0000000
--- a/build_ide/VS2010/flatsamplebinary.vcxproj
+++ /dev/null
@@ -1,273 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <ItemGroup Label="ProjectConfigurations">
-    <ProjectConfiguration Include="Debug|Win32">
-      <Configuration>Debug</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Debug|x64">
-      <Configuration>Debug</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|Win32">
-      <Configuration>Release</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|x64">
-      <Configuration>Release</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-  </ItemGroup>
-  <PropertyGroup Label="Globals">
-    <ProjectGUID>{16FA5518-3DE1-4B15-A1E0-F4734C276FB4}</ProjectGUID>
-    <Keyword>Win32Proj</Keyword>
-    <Platform>Win32</Platform>
-    <ProjectName>flatsamplebinary</ProjectName>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
-  <ImportGroup Label="ExtensionSettings">
-  </ImportGroup>
-  <ImportGroup Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
-  </ImportGroup>
-  <PropertyGroup Label="UserMacros" />
-  <PropertyGroup>
-    <_ProjectFileVersion>10.0.20506.1</_ProjectFileVersion>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flatsamplebinary.dir\Debug\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flatsamplebinary.dir\Debug\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flatsamplebinary</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flatsamplebinary</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</GenerateManifest>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flatsamplebinary.dir\Release\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flatsamplebinary.dir\Release\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flatsamplebinary</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flatsamplebinary</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</GenerateManifest>
-  </PropertyGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flatsamplebinary.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 /debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flatsamplebinary.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flatsamplebinary.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flatsamplebinary.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions>/debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flatsamplebinary.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flatsamplebinary.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flatsamplebinary.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flatsamplebinary.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flatsamplebinary.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flatsamplebinary.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flatsamplebinary.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flatsamplebinary.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemGroup>
-    <ClInclude Include="..\..\include\flatbuffers\flatbuffers.h" />
-    <ClInclude Include="..\..\samples\monster_generated.h" />
-    <ClCompile Include="..\..\samples\sample_binary.cpp" />
-  </ItemGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
-  <ImportGroup Label="ExtensionTargets">
-  </ImportGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/VS2010/flatsamplebinary.vcxproj.user b/build_ide/VS2010/flatsamplebinary.vcxproj.user
deleted file mode 100755
index a23c447..0000000
--- a/build_ide/VS2010/flatsamplebinary.vcxproj.user
+++ /dev/null
@@ -1,11 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/VS2010/flatsampletext.vcxproj b/build_ide/VS2010/flatsampletext.vcxproj
deleted file mode 100755
index 95a6a35..0000000
--- a/build_ide/VS2010/flatsampletext.vcxproj
+++ /dev/null
@@ -1,278 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <ItemGroup Label="ProjectConfigurations">
-    <ProjectConfiguration Include="Debug|Win32">
-      <Configuration>Debug</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Debug|x64">
-      <Configuration>Debug</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|Win32">
-      <Configuration>Release</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|x64">
-      <Configuration>Release</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-  </ItemGroup>
-  <PropertyGroup Label="Globals">
-    <ProjectGUID>{F0A15675-1017-4217-BB5B-3372F2C636AB}</ProjectGUID>
-    <Keyword>Win32Proj</Keyword>
-    <Platform>Win32</Platform>
-    <ProjectName>flatsampletext</ProjectName>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
-  <ImportGroup Label="ExtensionSettings">
-  </ImportGroup>
-  <ImportGroup Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
-  </ImportGroup>
-  <PropertyGroup Label="UserMacros" />
-  <PropertyGroup>
-    <_ProjectFileVersion>10.0.20506.1</_ProjectFileVersion>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flatsampletext.dir\Debug\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flatsampletext.dir\Debug\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flatsampletext</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flatsampletext</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</GenerateManifest>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flatsampletext.dir\Release\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flatsampletext.dir\Release\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flatsampletext</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flatsampletext</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</GenerateManifest>
-  </PropertyGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flatsampletext.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 /debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flatsampletext.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flatsampletext.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flatsampletext.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions>/debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flatsampletext.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flatsampletext.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flatsampletext.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flatsampletext.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flatsampletext.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flatsampletext.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flatsampletext.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flatsampletext.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemGroup>
-    <ClCompile Include="..\..\src\util.cpp" />
-    <ClInclude Include="..\..\include\flatbuffers\flatbuffers.h" />
-    <ClInclude Include="..\..\include\flatbuffers\idl.h" />
-    <ClInclude Include="..\..\include\flatbuffers\util.h" />
-    <ClInclude Include="..\..\samples\monster_generated.h" />
-    <ClCompile Include="..\..\src\idl_parser.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_text.cpp" />
-    <ClCompile Include="..\..\samples\sample_text.cpp" />
-  </ItemGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
-  <ImportGroup Label="ExtensionTargets">
-  </ImportGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/VS2010/flatsampletext.vcxproj.user b/build_ide/VS2010/flatsampletext.vcxproj.user
deleted file mode 100755
index 1753dbd..0000000
--- a/build_ide/VS2010/flatsampletext.vcxproj.user
+++ /dev/null
@@ -1,19 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/VS2010/flattests.vcxproj b/build_ide/VS2010/flattests.vcxproj
deleted file mode 100755
index 511aa66..0000000
--- a/build_ide/VS2010/flattests.vcxproj
+++ /dev/null
@@ -1,282 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <ItemGroup Label="ProjectConfigurations">
-    <ProjectConfiguration Include="Debug|Win32">
-      <Configuration>Debug</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Debug|x64">
-      <Configuration>Debug</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|Win32">
-      <Configuration>Release</Configuration>
-      <Platform>Win32</Platform>
-    </ProjectConfiguration>
-    <ProjectConfiguration Include="Release|x64">
-      <Configuration>Release</Configuration>
-      <Platform>x64</Platform>
-    </ProjectConfiguration>
-  </ItemGroup>
-  <PropertyGroup Label="Globals">
-    <ProjectGUID>{DC7BBA00-9FC6-48AF-B7E9-12CA91AC02AA}</ProjectGUID>
-    <Keyword>Win32Proj</Keyword>
-    <Platform>Win32</Platform>
-    <ProjectName>flattests</ProjectName>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
-    <ConfigurationType>Application</ConfigurationType>
-    <UseOfMfc>false</UseOfMfc>
-    <CharacterSet>MultiByte</CharacterSet>
-  </PropertyGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
-  <ImportGroup Label="ExtensionSettings">
-  </ImportGroup>
-  <ImportGroup Label="PropertySheets">
-    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
-  </ImportGroup>
-  <PropertyGroup Label="UserMacros" />
-  <PropertyGroup>
-    <_ProjectFileVersion>10.0.20506.1</_ProjectFileVersion>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flattests.dir\Debug\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flattests.dir\Debug\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">flattests</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">flattests</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</GenerateManifest>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(IntDir)</OutDir>
-    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(IntDir)</OutDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flattests.dir\Release\</IntDir>
-    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flattests.dir\Release\</IntDir>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">flattests</TargetName>
-    <TargetName Condition="'$(Configuration)|$(Platform)'=='Release|x64'">flattests</TargetName>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.exe</TargetExt>
-    <TargetExt Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.exe</TargetExt>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</LinkIncremental>
-    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</LinkIncremental>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</GenerateManifest>
-    <GenerateManifest Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</GenerateManifest>
-  </PropertyGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flattests.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 /debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flattests.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flattests.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>Disabled</InlineFunctionExpansion>
-      <Optimization>Disabled</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR="Debug";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Debug</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Debug/flattests.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;_DEBUG;CMAKE_INTDIR=\"Debug\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions>/debug %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>true</GenerateDebugInformation>
-      <ImportLibrary>../../Debug/flattests.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Debug/flattests.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flattests.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalOptions> /machine:X86 %(AdditionalOptions)</AdditionalOptions>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flattests.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flattests.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <ClCompile>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <CompileAs>CompileAsCpp</CompileAs>
-      <ExceptionHandling>Sync</ExceptionHandling>
-      <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
-      <Optimization>MaxSpeed</Optimization>
-      <PrecompiledHeader>NotUsing</PrecompiledHeader>
-      <RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
-      <RuntimeTypeInfo>true</RuntimeTypeInfo>
-      <WarningLevel>Level4</WarningLevel>
-      <DebugInformationFormat>
-      </DebugInformationFormat>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR="Release";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AssemblerListingLocation>Release</AssemblerListingLocation>
-      <ObjectFileName>$(IntDir)</ObjectFileName>
-      <ProgramDataBaseFileName>../../Release/flattests.pdb</ProgramDataBaseFileName>
-      <TreatWarningAsError>true</TreatWarningAsError>
-    </ClCompile>
-    <ResourceCompile>
-      <PreprocessorDefinitions>WIN32;_WINDOWS;NDEBUG;CMAKE_INTDIR=\"Release\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-    </ResourceCompile>
-    <Midl>
-      <AdditionalIncludeDirectories>../../include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
-      <OutputDirectory>$(IntDir)</OutputDirectory>
-      <HeaderFileName>%(Filename).h</HeaderFileName>
-      <TypeLibraryName>%(Filename).tlb</TypeLibraryName>
-      <InterfaceIdentifierFileName>%(Filename)_i.c</InterfaceIdentifierFileName>
-      <ProxyFileName>%(Filename)_p.c</ProxyFileName>
-    </Midl>
-    <Link>
-      <AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;winspool.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;comdlg32.lib;advapi32.lib</AdditionalDependencies>
-      <AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
-      <GenerateDebugInformation>false</GenerateDebugInformation>
-      <ImportLibrary>../../Release/flattests.lib</ImportLibrary>
-      <ProgramDataBaseFile>../../Release/flattests.pdb</ProgramDataBaseFile>
-      <SubSystem>Console</SubSystem>
-      <Version>
-      </Version>
-    </Link>
-    <ProjectReference>
-      <LinkLibraryDependencies>false</LinkLibraryDependencies>
-    </ProjectReference>
-  </ItemDefinitionGroup>
-  <ItemGroup>
-    <ClInclude Include="..\..\include\flatbuffers\flatbuffers.h" />
-    <ClInclude Include="..\..\include\flatbuffers\idl.h" />
-    <ClInclude Include="..\..\include\flatbuffers\reflection.h" />
-    <ClInclude Include="..\..\include\flatbuffers\util.h" />
-    <ClInclude Include="..\..\tests\monster_test_generated.h" />
-    <ClCompile Include="..\..\src\idl_gen_fbs.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_general.cpp" />
-    <ClCompile Include="..\..\src\idl_parser.cpp" />
-    <ClCompile Include="..\..\src\idl_gen_text.cpp" />
-    <ClCompile Include="..\..\src\reflection.cpp" />
-    <ClCompile Include="..\..\src\util.cpp" />
-    <ClCompile Include="..\..\tests\test.cpp" />
-  </ItemGroup>
-  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
-  <ImportGroup Label="ExtensionTargets">
-  </ImportGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/VS2010/flattests.vcxproj.user b/build_ide/VS2010/flattests.vcxproj.user
deleted file mode 100755
index 1753dbd..0000000
--- a/build_ide/VS2010/flattests.vcxproj.user
+++ /dev/null
@@ -1,19 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
-    <LocalDebuggerWorkingDirectory>..\..</LocalDebuggerWorkingDirectory>
-    <DebuggerFlavor>WindowsLocalDebugger</DebuggerFlavor>
-  </PropertyGroup>
-</Project>
\ No newline at end of file
diff --git a/build_ide/Xcode/FlatBuffers.xcodeproj/project.pbxproj b/build_ide/Xcode/FlatBuffers.xcodeproj/project.pbxproj
deleted file mode 100644
index ee18e9e..0000000
--- a/build_ide/Xcode/FlatBuffers.xcodeproj/project.pbxproj
+++ /dev/null
@@ -1,1099 +0,0 @@
-// !$*UTF8*$!
-{
-	archiveVersion = 1;
-	classes = {
-	};
-	objectVersion = 46;
-	objects = {
-
-/* Begin PBXBuildFile section */
-		1963D7D2A57344A3B1C1713F /* idl_parser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3709AC883348409592530AE6 /* idl_parser.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		5AC48C391ACA9A0A008132C5 /* idl_gen_general.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8CD8717A19CB937D0012A827 /* idl_gen_general.cpp */; };
-		61823BBC53544106B6DBC38E /* idl_parser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3709AC883348409592530AE6 /* idl_parser.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		61FF3C34FBEC4819A1C30F92 /* sample_text.cpp in Sources */ = {isa = PBXBuildFile; fileRef = ECCEBFFA6977404F858F9739 /* sample_text.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		8C2AAE0A1CB338A8000CC78D /* util.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C2AAE091CB338A8000CC78D /* util.cpp */; settings = {ASSET_TAGS = (); }; };
-		8C2AAE0B1CB338CD000CC78D /* util.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C2AAE091CB338A8000CC78D /* util.cpp */; settings = {ASSET_TAGS = (); }; };
-		8C2AAE0C1CB338CE000CC78D /* util.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C2AAE091CB338A8000CC78D /* util.cpp */; settings = {ASSET_TAGS = (); }; };
-		8C303C591975D6A700D7C1C5 /* idl_gen_go.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C303C581975D6A700D7C1C5 /* idl_gen_go.cpp */; };
-		8C6905FD19F835B400CB8866 /* idl_gen_fbs.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C6905EC19F8357300CB8866 /* idl_gen_fbs.cpp */; };
-		8C78573E1BD5AE2C00C53C34 /* idl_gen_js.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C78573D1BD5AE2C00C53C34 /* idl_gen_js.cpp */; };
-		8C8774631B703D4800E693F5 /* reflection.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C8774621B703D4800E693F5 /* reflection.cpp */; };
-		8C8774641B703E1200E693F5 /* idl_gen_fbs.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8C6905EC19F8357300CB8866 /* idl_gen_fbs.cpp */; };
-		8CA854B31B04244A00040A06 /* idl_gen_python.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8CA854B21B04244A00040A06 /* idl_gen_python.cpp */; };
-		8CD8717B19CB937D0012A827 /* idl_gen_general.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8CD8717A19CB937D0012A827 /* idl_gen_general.cpp */; };
-		A9C9A99F719A4ED58DC2D2FC /* idl_parser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3709AC883348409592530AE6 /* idl_parser.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		AA9BACF55EB3456BA2F633BB /* flatc.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0DFD29781D8E490284B06504 /* flatc.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		AD71FEBEE4E846529002C1F0 /* idl_gen_text.cpp in Sources */ = {isa = PBXBuildFile; fileRef = F6C5D81DBF864365B12E269D /* idl_gen_text.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		AE5F47A7DCB44781B657F062 /* idl_gen_text.cpp in Sources */ = {isa = PBXBuildFile; fileRef = F6C5D81DBF864365B12E269D /* idl_gen_text.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		BE03D7B0C9584DD58B50ED34 /* idl_gen_cpp.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD90A7F6B2BE4D0384294DD1 /* idl_gen_cpp.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		D2DA271D1BFFBC06000F9168 /* idl_gen_php.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D2DA271C1BFFBC06000F9168 /* idl_gen_php.cpp */; };
-		E0680D6B5BFD484BA9D88EE8 /* idl_gen_text.cpp in Sources */ = {isa = PBXBuildFile; fileRef = F6C5D81DBF864365B12E269D /* idl_gen_text.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		E84E4B7612DF4C369DC24843 /* sample_binary.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 5EE44BFFAF8E43F485859145 /* sample_binary.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-		EE4AEE138D684B30A1BF5462 /* test.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 6AD24EEB3D024825A37741FF /* test.cpp */; settings = {COMPILER_FLAGS = ""; }; };
-/* End PBXBuildFile section */
-
-/* Begin PBXFileReference section */
-		00154BD8654B4B5B9FF45FA6 /* idl.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = idl.h; path = include/flatbuffers/idl.h; sourceTree = SOURCE_ROOT; };
-		0DFD29781D8E490284B06504 /* flatc.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = flatc.cpp; path = src/flatc.cpp; sourceTree = SOURCE_ROOT; };
-		18185F364F604E648CF6EE25 /* flatc */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; path = flatc; sourceTree = BUILT_PRODUCTS_DIR; };
-		3709AC883348409592530AE6 /* idl_parser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_parser.cpp; path = src/idl_parser.cpp; sourceTree = SOURCE_ROOT; };
-		3863042BCEC64791BFB48625 /* flatsamplebinary */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; path = flatsamplebinary; sourceTree = BUILT_PRODUCTS_DIR; };
-		420E3BC724ED4A008D79297F /* flatsampletext */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; path = flatsampletext; sourceTree = BUILT_PRODUCTS_DIR; };
-		5EE44BFFAF8E43F485859145 /* sample_binary.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = sample_binary.cpp; path = samples/sample_binary.cpp; sourceTree = SOURCE_ROOT; };
-		6AD24EEB3D024825A37741FF /* test.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = test.cpp; path = tests/test.cpp; sourceTree = SOURCE_ROOT; };
-		8C2AAE091CB338A8000CC78D /* util.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = util.cpp; path = src/util.cpp; sourceTree = "<group>"; };
-		8C303C581975D6A700D7C1C5 /* idl_gen_go.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_go.cpp; path = src/idl_gen_go.cpp; sourceTree = "<group>"; };
-		8C6905EC19F8357300CB8866 /* idl_gen_fbs.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_fbs.cpp; path = src/idl_gen_fbs.cpp; sourceTree = "<group>"; };
-		8C78573D1BD5AE2C00C53C34 /* idl_gen_js.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_js.cpp; path = src/idl_gen_js.cpp; sourceTree = "<group>"; };
-		8C8774621B703D4800E693F5 /* reflection.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = reflection.cpp; path = src/reflection.cpp; sourceTree = "<group>"; };
-		8CA854B21B04244A00040A06 /* idl_gen_python.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_python.cpp; path = src/idl_gen_python.cpp; sourceTree = "<group>"; };
-		8CD8717A19CB937D0012A827 /* idl_gen_general.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_general.cpp; path = src/idl_gen_general.cpp; sourceTree = "<group>"; };
-		A13F25CDAD23435DA293690D /* flattests */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; path = flattests; sourceTree = BUILT_PRODUCTS_DIR; };
-		AB70F1FBA50E4120BCF37C8D /* monster_test_generated.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = monster_test_generated.h; path = tests/monster_test_generated.h; sourceTree = SOURCE_ROOT; };
-		C0E7B66C3FF849A0AD9A7168 /* util.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = util.h; path = include/flatbuffers/util.h; sourceTree = SOURCE_ROOT; };
-		CD90A7F6B2BE4D0384294DD1 /* idl_gen_cpp.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_cpp.cpp; path = src/idl_gen_cpp.cpp; sourceTree = SOURCE_ROOT; };
-		D2DA271C1BFFBC06000F9168 /* idl_gen_php.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_php.cpp; path = src/idl_gen_php.cpp; sourceTree = "<group>"; };
-		DD8B353D4756412195777FBA /* flatbuffers.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = flatbuffers.h; path = include/flatbuffers/flatbuffers.h; sourceTree = SOURCE_ROOT; };
-		ECCEBFFA6977404F858F9739 /* sample_text.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = sample_text.cpp; path = samples/sample_text.cpp; sourceTree = SOURCE_ROOT; };
-		F6C5D81DBF864365B12E269D /* idl_gen_text.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = idl_gen_text.cpp; path = src/idl_gen_text.cpp; sourceTree = SOURCE_ROOT; };
-/* End PBXFileReference section */
-
-/* Begin PBXGroup section */
-		28237E300FE042DEADA302D3 /* Source Files */ = {
-			isa = PBXGroup;
-			children = (
-				8C2AAE091CB338A8000CC78D /* util.cpp */,
-				D2DA271C1BFFBC06000F9168 /* idl_gen_php.cpp */,
-				8C78573D1BD5AE2C00C53C34 /* idl_gen_js.cpp */,
-				8CA854B21B04244A00040A06 /* idl_gen_python.cpp */,
-				8C6905EC19F8357300CB8866 /* idl_gen_fbs.cpp */,
-				8CD8717A19CB937D0012A827 /* idl_gen_general.cpp */,
-				8C303C581975D6A700D7C1C5 /* idl_gen_go.cpp */,
-				F6C5D81DBF864365B12E269D /* idl_gen_text.cpp */,
-				3709AC883348409592530AE6 /* idl_parser.cpp */,
-				CD90A7F6B2BE4D0384294DD1 /* idl_gen_cpp.cpp */,
-				8C8774621B703D4800E693F5 /* reflection.cpp */,
-			);
-			name = "Source Files";
-			sourceTree = "<group>";
-		};
-		378446B9D5EF46EF92B35E21 /* flatc */ = {
-			isa = PBXGroup;
-			children = (
-				0DFD29781D8E490284B06504 /* flatc.cpp */,
-			);
-			name = flatc;
-			sourceTree = "<group>";
-		};
-		5FEA84E7D39645988300317C /* Header Files */ = {
-			isa = PBXGroup;
-			children = (
-				DD8B353D4756412195777FBA /* flatbuffers.h */,
-				00154BD8654B4B5B9FF45FA6 /* idl.h */,
-				C0E7B66C3FF849A0AD9A7168 /* util.h */,
-			);
-			name = "Header Files";
-			sourceTree = "<group>";
-		};
-		866694F9F2F7451382D236B3 /* Sources */ = {
-			isa = PBXGroup;
-			children = (
-				28237E300FE042DEADA302D3 /* Source Files */,
-				5FEA84E7D39645988300317C /* Header Files */,
-				378446B9D5EF46EF92B35E21 /* flatc */,
-				DB9DE41C20F349F694A488F3 /* flatsamplebinary */,
-				8FA1F43C78914AE5AD04E24E /* flatsampletext */,
-				88421F5F87584EE3B67C979A /* flattests */,
-			);
-			name = Sources;
-			sourceTree = "<group>";
-		};
-		88421F5F87584EE3B67C979A /* flattests */ = {
-			isa = PBXGroup;
-			children = (
-				AB70F1FBA50E4120BCF37C8D /* monster_test_generated.h */,
-				6AD24EEB3D024825A37741FF /* test.cpp */,
-			);
-			name = flattests;
-			sourceTree = "<group>";
-		};
-		8F5E926B72104F4194B3BD5A = {
-			isa = PBXGroup;
-			children = (
-				866694F9F2F7451382D236B3 /* Sources */,
-				99CC11E382B8420AA79A8A14 /* Products */,
-			);
-			sourceTree = "<group>";
-		};
-		8FA1F43C78914AE5AD04E24E /* flatsampletext */ = {
-			isa = PBXGroup;
-			children = (
-				ECCEBFFA6977404F858F9739 /* sample_text.cpp */,
-			);
-			name = flatsampletext;
-			sourceTree = "<group>";
-		};
-		99CC11E382B8420AA79A8A14 /* Products */ = {
-			isa = PBXGroup;
-			children = (
-				18185F364F604E648CF6EE25 /* flatc */,
-				3863042BCEC64791BFB48625 /* flatsamplebinary */,
-				420E3BC724ED4A008D79297F /* flatsampletext */,
-				A13F25CDAD23435DA293690D /* flattests */,
-			);
-			name = Products;
-			sourceTree = "<group>";
-		};
-		DB9DE41C20F349F694A488F3 /* flatsamplebinary */ = {
-			isa = PBXGroup;
-			children = (
-				5EE44BFFAF8E43F485859145 /* sample_binary.cpp */,
-			);
-			name = flatsamplebinary;
-			sourceTree = "<group>";
-		};
-/* End PBXGroup section */
-
-/* Begin PBXNativeTarget section */
-		49A8585B4DDF45E9A3B17CFC /* flatc */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = 33E06AF34F9D4985A3ECC3BE /* Build configuration list for PBXNativeTarget "flatc" */;
-			buildPhases = (
-				BA2D863987DC44ADBA112566 /* Sources */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-			);
-			name = flatc;
-			productName = flatc;
-			productReference = 18185F364F604E648CF6EE25 /* flatc */;
-			productType = "com.apple.product-type.tool";
-		};
-		6FAE4035E73E43A4B85484F5 /* flatsamplebinary */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = 00270D02D60C49CBA8254F7E /* Build configuration list for PBXNativeTarget "flatsamplebinary" */;
-			buildPhases = (
-				B52C93947E644572857F437C /* Sources */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-			);
-			name = flatsamplebinary;
-			productName = flatsamplebinary;
-			productReference = 3863042BCEC64791BFB48625 /* flatsamplebinary */;
-			productType = "com.apple.product-type.tool";
-		};
-		D69F7F780CCE4A07821AC50E /* flattests */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = 368F4ABC4CF54353A6440842 /* Build configuration list for PBXNativeTarget "flattests" */;
-			buildPhases = (
-				F45B105DA30F42048C359289 /* Sources */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-			);
-			name = flattests;
-			productName = flattests;
-			productReference = A13F25CDAD23435DA293690D /* flattests */;
-			productType = "com.apple.product-type.tool";
-		};
-		DBAB5216DC474DD19C4A3A9D /* flatsampletext */ = {
-			isa = PBXNativeTarget;
-			buildConfigurationList = 4EFA62D61D724785A337C00C /* Build configuration list for PBXNativeTarget "flatsampletext" */;
-			buildPhases = (
-				A5F04AC5C7354005A3736470 /* Sources */,
-			);
-			buildRules = (
-			);
-			dependencies = (
-			);
-			name = flatsampletext;
-			productName = flatsampletext;
-			productReference = 420E3BC724ED4A008D79297F /* flatsampletext */;
-			productType = "com.apple.product-type.tool";
-		};
-/* End PBXNativeTarget section */
-
-/* Begin PBXProject section */
-		17AD84829D614C168858FC02 /* Project object */ = {
-			isa = PBXProject;
-			attributes = {
-				BuildIndependentTargetsInParallel = YES;
-				LastUpgradeCheck = 0700;
-			};
-			buildConfigurationList = 6428BEB363AA4E03A282AA8C /* Build configuration list for PBXProject "FlatBuffers" */;
-			compatibilityVersion = "Xcode 3.2";
-			developmentRegion = English;
-			hasScannedForEncodings = 0;
-			knownRegions = (
-				en,
-			);
-			mainGroup = 8F5E926B72104F4194B3BD5A;
-			projectDirPath = ../..;
-			projectRoot = "";
-			targets = (
-				49A8585B4DDF45E9A3B17CFC /* flatc */,
-				6FAE4035E73E43A4B85484F5 /* flatsamplebinary */,
-				DBAB5216DC474DD19C4A3A9D /* flatsampletext */,
-				D69F7F780CCE4A07821AC50E /* flattests */,
-			);
-		};
-/* End PBXProject section */
-
-/* Begin PBXSourcesBuildPhase section */
-		A5F04AC5C7354005A3736470 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				61FF3C34FBEC4819A1C30F92 /* sample_text.cpp in Sources */,
-				AE5F47A7DCB44781B657F062 /* idl_gen_text.cpp in Sources */,
-				1963D7D2A57344A3B1C1713F /* idl_parser.cpp in Sources */,
-				8C2AAE0B1CB338CD000CC78D /* util.cpp in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		B52C93947E644572857F437C /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				E84E4B7612DF4C369DC24843 /* sample_binary.cpp in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		BA2D863987DC44ADBA112566 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				8C303C591975D6A700D7C1C5 /* idl_gen_go.cpp in Sources */,
-				AA9BACF55EB3456BA2F633BB /* flatc.cpp in Sources */,
-				BE03D7B0C9584DD58B50ED34 /* idl_gen_cpp.cpp in Sources */,
-				AD71FEBEE4E846529002C1F0 /* idl_gen_text.cpp in Sources */,
-				8C2AAE0A1CB338A8000CC78D /* util.cpp in Sources */,
-				8C8774641B703E1200E693F5 /* idl_gen_fbs.cpp in Sources */,
-				A9C9A99F719A4ED58DC2D2FC /* idl_parser.cpp in Sources */,
-				8CA854B31B04244A00040A06 /* idl_gen_python.cpp in Sources */,
-				8CD8717B19CB937D0012A827 /* idl_gen_general.cpp in Sources */,
-				8C78573E1BD5AE2C00C53C34 /* idl_gen_js.cpp in Sources */,
-				D2DA271D1BFFBC06000F9168 /* idl_gen_php.cpp in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		F45B105DA30F42048C359289 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				8C8774631B703D4800E693F5 /* reflection.cpp in Sources */,
-				5AC48C391ACA9A0A008132C5 /* idl_gen_general.cpp in Sources */,
-				8C2AAE0C1CB338CE000CC78D /* util.cpp in Sources */,
-				8C6905FD19F835B400CB8866 /* idl_gen_fbs.cpp in Sources */,
-				E0680D6B5BFD484BA9D88EE8 /* idl_gen_text.cpp in Sources */,
-				61823BBC53544106B6DBC38E /* idl_parser.cpp in Sources */,
-				EE4AEE138D684B30A1BF5462 /* test.cpp in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-/* End PBXSourcesBuildPhase section */
-
-/* Begin XCBuildConfiguration section */
-		02575EDE5A1349C9A3584E32 /* RelWithDebInfo */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CONFIGURATION_BUILD_DIR = .;
-				ONLY_ACTIVE_ARCH = YES;
-				SDKROOT = macosx;
-				SYMROOT = build;
-			};
-			name = RelWithDebInfo;
-		};
-		04681CC521204B3B87BB1E81 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_EMPTY_BODY = YES;
-				CLANG_WARN_IMPLICIT_SIGN_CONVERSION = NO;
-				CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES;
-				CLANG_WARN_UNREACHABLE_CODE = YES;
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 0;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				GCC_TREAT_IMPLICIT_FUNCTION_DECLARATIONS_AS_ERRORS = YES;
-				GCC_TREAT_INCOMPATIBLE_POINTER_TYPE_WARNINGS_AS_ERRORS = YES;
-				GCC_TREAT_WARNINGS_AS_ERRORS = YES;
-				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
-				GCC_WARN_ABOUT_MISSING_FIELD_INITIALIZERS = YES;
-				GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
-				GCC_WARN_ABOUT_MISSING_PROTOTYPES = NO;
-				GCC_WARN_ABOUT_RETURN_TYPE = YES;
-				GCC_WARN_FOUR_CHARACTER_CONSTANTS = YES;
-				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
-				GCC_WARN_PEDANTIC = YES;
-				GCC_WARN_SHADOW = YES;
-				GCC_WARN_SIGN_COMPARE = YES;
-				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
-				GCC_WARN_UNKNOWN_PRAGMAS = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_LABEL = YES;
-				GCC_WARN_UNUSED_PARAMETER = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = "     -std=c++0x";
-				OTHER_CPLUSPLUSFLAGS = "     -std=c++0x";
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flattests;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Debug;
-		};
-		1399048C48224B1BBEF356B7 /* RelWithDebInfo */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 2;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsamplebinary;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = RelWithDebInfo;
-		};
-		1C94D755C4754814BABC99DF /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 0;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = "     -std=c++0x";
-				OTHER_CPLUSPLUSFLAGS = "     -std=c++0x";
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsamplebinary;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Debug;
-		};
-		33335DE09CF844709E9E4AA9 /* RelWithDebInfo */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_EMPTY_BODY = YES;
-				CLANG_WARN_IMPLICIT_SIGN_CONVERSION = NO;
-				CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES;
-				CLANG_WARN_UNREACHABLE_CODE = YES;
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 2;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				GCC_TREAT_IMPLICIT_FUNCTION_DECLARATIONS_AS_ERRORS = YES;
-				GCC_TREAT_INCOMPATIBLE_POINTER_TYPE_WARNINGS_AS_ERRORS = YES;
-				GCC_TREAT_WARNINGS_AS_ERRORS = YES;
-				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
-				GCC_WARN_ABOUT_MISSING_FIELD_INITIALIZERS = YES;
-				GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
-				GCC_WARN_ABOUT_MISSING_PROTOTYPES = NO;
-				GCC_WARN_ABOUT_RETURN_TYPE = YES;
-				GCC_WARN_FOUR_CHARACTER_CONSTANTS = YES;
-				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
-				GCC_WARN_PEDANTIC = YES;
-				GCC_WARN_SHADOW = YES;
-				GCC_WARN_SIGN_COMPARE = YES;
-				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
-				GCC_WARN_UNKNOWN_PRAGMAS = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_LABEL = YES;
-				GCC_WARN_UNUSED_PARAMETER = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flattests;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = RelWithDebInfo;
-		};
-		33B3983234F648E28F058235 /* MinSizeRel */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_EMPTY_BODY = YES;
-				CLANG_WARN_IMPLICIT_SIGN_CONVERSION = NO;
-				CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES;
-				CLANG_WARN_UNREACHABLE_CODE = YES;
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = s;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				GCC_TREAT_IMPLICIT_FUNCTION_DECLARATIONS_AS_ERRORS = YES;
-				GCC_TREAT_INCOMPATIBLE_POINTER_TYPE_WARNINGS_AS_ERRORS = YES;
-				GCC_TREAT_WARNINGS_AS_ERRORS = YES;
-				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
-				GCC_WARN_ABOUT_MISSING_FIELD_INITIALIZERS = YES;
-				GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
-				GCC_WARN_ABOUT_MISSING_PROTOTYPES = NO;
-				GCC_WARN_ABOUT_RETURN_TYPE = YES;
-				GCC_WARN_FOUR_CHARACTER_CONSTANTS = YES;
-				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
-				GCC_WARN_PEDANTIC = YES;
-				GCC_WARN_SHADOW = YES;
-				GCC_WARN_SIGN_COMPARE = YES;
-				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
-				GCC_WARN_UNKNOWN_PRAGMAS = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_LABEL = YES;
-				GCC_WARN_UNUSED_PARAMETER = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flattests;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = MinSizeRel;
-		};
-		370A0A2C8AA943C19C8021C9 /* MinSizeRel */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = s;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsamplebinary;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = MinSizeRel;
-		};
-		37C0FFB777CF4C19BD7AA662 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_EMPTY_BODY = YES;
-				CLANG_WARN_IMPLICIT_SIGN_CONVERSION = NO;
-				CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES;
-				CLANG_WARN_UNREACHABLE_CODE = YES;
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 3;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				GCC_TREAT_IMPLICIT_FUNCTION_DECLARATIONS_AS_ERRORS = YES;
-				GCC_TREAT_INCOMPATIBLE_POINTER_TYPE_WARNINGS_AS_ERRORS = YES;
-				GCC_TREAT_WARNINGS_AS_ERRORS = YES;
-				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
-				GCC_WARN_ABOUT_MISSING_FIELD_INITIALIZERS = YES;
-				GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
-				GCC_WARN_ABOUT_MISSING_PROTOTYPES = NO;
-				GCC_WARN_ABOUT_RETURN_TYPE = YES;
-				GCC_WARN_FOUR_CHARACTER_CONSTANTS = YES;
-				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
-				GCC_WARN_PEDANTIC = YES;
-				GCC_WARN_SHADOW = YES;
-				GCC_WARN_SIGN_COMPARE = YES;
-				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
-				GCC_WARN_UNKNOWN_PRAGMAS = YES;
-				GCC_WARN_UNUSED_FUNCTION = YES;
-				GCC_WARN_UNUSED_LABEL = YES;
-				GCC_WARN_UNUSED_PARAMETER = YES;
-				GCC_WARN_UNUSED_VARIABLE = YES;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flattests;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Release;
-		};
-		41E4007D1858418CA3E8465E /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 3;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsampletext;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Release;
-		};
-		48205B66908F4F23861A62D1 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 3;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatc;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Release;
-		};
-		49C655ECBF114257BDDB1F8C /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 0;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = "     -std=c++0x";
-				OTHER_CPLUSPLUSFLAGS = "     -std=c++0x";
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatc;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Debug;
-		};
-		4D59EB9A2B114E4A80EE8969 /* RelWithDebInfo */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 2;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatc;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = RelWithDebInfo;
-		};
-		60917B4900A4484898ED29EF /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CONFIGURATION_BUILD_DIR = .;
-				ENABLE_TESTABILITY = YES;
-				ONLY_ACTIVE_ARCH = YES;
-				SDKROOT = macosx;
-				SYMROOT = build;
-			};
-			name = Debug;
-		};
-		65B8F01CB7E6407CB262E6B6 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CONFIGURATION_BUILD_DIR = .;
-				ONLY_ACTIVE_ARCH = YES;
-				SDKROOT = macosx;
-				SYMROOT = build;
-			};
-			name = Release;
-		};
-		720E13DCA0B94E778BBED2DD /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 3;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsamplebinary;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Release;
-		};
-		7ACE0191E05A40DEBBE068EE /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 0;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = "     -std=c++0x";
-				OTHER_CPLUSPLUSFLAGS = "     -std=c++0x";
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsampletext;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = Debug;
-		};
-		A38FA2E52874442987B7F331 /* MinSizeRel */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = s;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatc;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = MinSizeRel;
-		};
-		C1F9C4F8E9654F90B78B41DE /* MinSizeRel */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = s;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsampletext;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = MinSizeRel;
-		};
-		C839EDC9489F432994623A13 /* MinSizeRel */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CONFIGURATION_BUILD_DIR = .;
-				ONLY_ACTIVE_ARCH = YES;
-				SDKROOT = macosx;
-				SYMROOT = build;
-			};
-			name = MinSizeRel;
-		};
-		F483DAC3AB084D769E89CBDF /* RelWithDebInfo */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				COMBINE_HIDPI_IMAGES = YES;
-				EXECUTABLE_PREFIX = "";
-				EXECUTABLE_SUFFIX = "";
-				GCC_GENERATE_DEBUGGING_SYMBOLS = YES;
-				GCC_INLINES_ARE_PRIVATE_EXTERN = NO;
-				GCC_OPTIMIZATION_LEVEL = 2;
-				GCC_PREPROCESSOR_DEFINITIONS = "'CMAKE_INTDIR=\"$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)\"'";
-				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
-				HEADER_SEARCH_PATHS = "$(PROJECT_DIR)/include";
-				INSTALL_PATH = "";
-				LIBRARY_SEARCH_PATHS = "";
-				OTHER_CFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_CPLUSPLUSFLAGS = (
-					"-DNDEBUG",
-					"-std=c++0x",
-				);
-				OTHER_LDFLAGS = (
-					"-Wl,-search_paths_first",
-					"-Wl,-headerpad_max_install_names",
-				);
-				OTHER_REZFLAGS = "";
-				PRODUCT_NAME = flatsampletext;
-				SECTORDER_FLAGS = "";
-				SYMROOT = build;
-				USE_HEADERMAP = NO;
-				WARNING_CFLAGS = (
-					"-Wmost",
-					"-Wno-four-char-constants",
-					"-Wno-unknown-pragmas",
-				);
-			};
-			name = RelWithDebInfo;
-		};
-/* End XCBuildConfiguration section */
-
-/* Begin XCConfigurationList section */
-		00270D02D60C49CBA8254F7E /* Build configuration list for PBXNativeTarget "flatsamplebinary" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				1C94D755C4754814BABC99DF /* Debug */,
-				720E13DCA0B94E778BBED2DD /* Release */,
-				370A0A2C8AA943C19C8021C9 /* MinSizeRel */,
-				1399048C48224B1BBEF356B7 /* RelWithDebInfo */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Debug;
-		};
-		33E06AF34F9D4985A3ECC3BE /* Build configuration list for PBXNativeTarget "flatc" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				49C655ECBF114257BDDB1F8C /* Debug */,
-				48205B66908F4F23861A62D1 /* Release */,
-				A38FA2E52874442987B7F331 /* MinSizeRel */,
-				4D59EB9A2B114E4A80EE8969 /* RelWithDebInfo */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Debug;
-		};
-		368F4ABC4CF54353A6440842 /* Build configuration list for PBXNativeTarget "flattests" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				04681CC521204B3B87BB1E81 /* Debug */,
-				37C0FFB777CF4C19BD7AA662 /* Release */,
-				33B3983234F648E28F058235 /* MinSizeRel */,
-				33335DE09CF844709E9E4AA9 /* RelWithDebInfo */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Debug;
-		};
-		4EFA62D61D724785A337C00C /* Build configuration list for PBXNativeTarget "flatsampletext" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				7ACE0191E05A40DEBBE068EE /* Debug */,
-				41E4007D1858418CA3E8465E /* Release */,
-				C1F9C4F8E9654F90B78B41DE /* MinSizeRel */,
-				F483DAC3AB084D769E89CBDF /* RelWithDebInfo */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Debug;
-		};
-		6428BEB363AA4E03A282AA8C /* Build configuration list for PBXProject "FlatBuffers" */ = {
-			isa = XCConfigurationList;
-			buildConfigurations = (
-				60917B4900A4484898ED29EF /* Debug */,
-				65B8F01CB7E6407CB262E6B6 /* Release */,
-				C839EDC9489F432994623A13 /* MinSizeRel */,
-				02575EDE5A1349C9A3584E32 /* RelWithDebInfo */,
-			);
-			defaultConfigurationIsVisible = 0;
-			defaultConfigurationName = Debug;
-		};
-/* End XCConfigurationList section */
-	};
-	rootObject = 17AD84829D614C168858FC02 /* Project object */;
-}
diff --git a/docs/source/Building.md b/docs/source/Building.md
index f57371d..daeeb1e 100755
--- a/docs/source/Building.md
+++ b/docs/source/Building.md
@@ -1,14 +1,9 @@
 Building    {#flatbuffers_guide_building}
 ========
 
-## Building with Visual Studio or Xcode projects
-
-There are project files for Visual Studio and Xcode that should allow you
-to build the compiler `flatc`, the samples and the tests out of the box.
-
 ## Building with CMake
 
-Alternatively, the distribution comes with a `cmake` file that should allow
+The distribution comes with a `cmake` file that should allow
 you to build project/make files for any platform. For details on `cmake`, see
 <http://www.cmake.org>. In brief, depending on your platform, use one of
 e.g.:
diff --git a/docs/source/Compiler.md b/docs/source/Compiler.md
index ad584c7..b71b8c4 100755
--- a/docs/source/Compiler.md
+++ b/docs/source/Compiler.md
@@ -81,6 +81,11 @@
 -   `--gen-mutable` : Generate additional non-const accessors for mutating
     FlatBuffers in-place.
 
+    `--gen-object-api` : Generate an additional object-based API. This API is
+    more convenient for object construction and mutation than the base API,
+    at the cost of efficiency (object allocation). Recommended only to be used
+    if other options are insufficient.
+
 -   `--gen-onefile` :  Generate single output file (useful for C#)
 
 -   `--gen-all`: Generate not just code for the current schema files, but
@@ -103,5 +108,9 @@
     to the reflection/reflection.fbs schema. Loading this binary file is the
     basis for reflection functionality.
 
+-   `--conform FILE` : Specify a schema the following schemas should be
+    an evolution of. Gives errors if not. Useful to check if schema
+    modifications don't break schema evolution rules.
+
 NOTE: short-form options for generators are deprecated, use the long form
 whenever possible.
diff --git a/docs/source/CppUsage.md b/docs/source/CppUsage.md
index d4abe66..4a9c78e 100755
--- a/docs/source/CppUsage.md
+++ b/docs/source/CppUsage.md
@@ -85,6 +85,55 @@
 
 *Note: That we never stored a `mana` value, so it will return the default.*
 
+## Object based API.
+
+FlatBuffers is all about memory efficiency, which is why its base API is written
+around using as little as possible of it. This does make the API clumsier
+(requiring pre-order construction of all data, and making mutation harder).
+
+For times when efficiency is less important a more convenient object based API
+can be used (through `--gen-object-api`) that is able to unpack & pack a
+FlatBuffer into objects and standard STL containers, allowing for convenient
+construction, access and mutation.
+
+To use:
+
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~{.cpp}
+    auto monsterobj = UnpackMonster(buffer);
+    cout << monsterobj->name;  // This is now a std::string!
+    monsterobj->name = "Bob";  // Change the name.
+    FlatBufferBuilder fbb;
+    CreateMonster(fbb, monsterobj.get());     // Serialize into new buffer.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+# External references.
+
+An additional feature of the object API is the ability to allow you to load
+multiple independent FlatBuffers, and have them refer to eachothers objects
+using hashes which are then represented as typed pointers in the object API.
+
+To make this work have a field in the objects you want to referred to which is
+using the string hashing feature (see `hash` attribute in the
+[schema](@ref flatbuffers_guide_writing_schema) documentation). Then you have
+a similar hash in the field referring to it, along with a `cpp_type`
+attribute specifying the C++ type this will refer to (this can be any C++
+type, and will get a `*` added).
+
+Then, in JSON or however you create these buffers, make sure they use the
+same string (or hash).
+
+When you call `UnPack` (or `Create`), you'll need a function that maps from
+hash to the object (see `resolver_function_t` for details).
+
+# Using different pointer types.
+
+By default the object tree is built out of `std::unique_ptr`, but you can
+influence this either globally (using the `--cpp-ptr-type` argument to
+`flatc`) or per field (using the `cpp_ptr_type` attribute) to by any smart
+pointer type (`my_ptr<T>`), or by specifying `naked` as the type to get `T *`
+pointers. Unlike the smart pointers, naked pointers do not manage memory for
+you, so you'll have to manage their lifecycles manually.
+
 ## Reflection (& Resizing)
 
 There is experimental support for reflection in FlatBuffers, allowing you to
diff --git a/docs/source/GoUsage.md b/docs/source/GoUsage.md
index a3a0e92..ab6ddbd 100644
--- a/docs/source/GoUsage.md
+++ b/docs/source/GoUsage.md
@@ -67,6 +67,29 @@
     pos := monster.Pos(nil)
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
+
+In some cases it's necessary to modify values in an existing FlatBuffer in place (without creating a copy). For this reason, scalar fields of a Flatbuffer table or struct can be mutated.
+
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~{.go}
+    monster := example.GetRootAsMonster(buf, 0)
+
+    // Set table field.
+    if ok := monster.MutateHp(10); !ok {
+      panic("failed to mutate Hp")
+    }
+
+    // Set struct field.
+    monster.Pos().MutateZ(4)
+
+    // This mutation will fail because the mana field is not available in
+    // the buffer. It should be set when creating the buffer.
+    if ok := monster.MutateMana(20); !ok {
+      panic("failed to mutate Hp")
+    }
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+The term `mutate` is used instead of `set` to indicate that this is a special use case. All mutate functions return a boolean value which is false if the field we're trying to mutate is not available in the buffer.
+
 ## Text Parsing
 
 There currently is no support for parsing text (Schema's and JSON) directly
diff --git a/docs/source/JavaCsharpUsage.md b/docs/source/JavaCsharpUsage.md
index 3af9cfa..cc58f85 100755
--- a/docs/source/JavaCsharpUsage.md
+++ b/docs/source/JavaCsharpUsage.md
@@ -131,6 +131,36 @@
     monster.GetPos(preconstructedPos);
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
+## Storing dictionaries in a FlatBuffer
+
+FlatBuffers doesn't support dictionaries natively, but there is support to
+emulate their behavior with vectors and binary search, which means you
+can have fast lookups directly from a FlatBuffer without having to unpack
+your data into a `Dictionary` or similar.
+
+To use it:
+-   Designate one of the fields in a table as they "key" field. You do this
+    by setting the `key` attribute on this field, e.g.
+    `name:string (key)`.
+    You may only have one key field, and it must be of string or scalar type.
+-   Write out tables of this type as usual, collect their offsets in an
+    array.
+-   Instead of calling standard generated method,
+    e.g.: `Monster.createTestarrayoftablesVector`,
+    call `CreateMySortedVectorOfTables` in C# or
+    `createSortedVectorOfTables` (from the `FlatBufferBuilder` object) in Java,
+    which will first sort all offsets such that the tables they refer to
+    are sorted by the key field, then serialize it.
+-   Now when you're accessing the FlatBuffer, you can use `LookupByKey`
+    to access elements of the vector, e.g.:
+    `Monster.lookupByKey(tablesVectorOffset, "Frodo", dataBuffer)`,
+    which returns an object of the corresponding table type,
+    or `null` if not found.
+    `LookupByKey` performs a binary search, so should have a similar speed to
+    `Dictionary`, though may be faster because of better caching. `LookupByKey`
+    only works if the vector has been sorted, it will likely not find elements
+    if it hasn't been sorted.
+
 ## Text parsing
 
 There currently is no support for parsing text (Schema's and JSON) directly
diff --git a/docs/source/Schemas.md b/docs/source/Schemas.md
index 5bcaccb..f9fe486 100755
--- a/docs/source/Schemas.md
+++ b/docs/source/Schemas.md
@@ -304,6 +304,10 @@
 -   `key` (on a field): this field is meant to be used as a key when sorting
     a vector of the type of table it sits in. Can be used for in-place
     binary search.
+-   `hash` (on a field). This is an (un)signed 32/64 bit integer field, whose
+    value during JSON parsing is allowed to be a string, which will then be
+    stored as its hash. The value of attribute is the hashing algorithm to
+    use, one of `fnv1_32` `fnv1_64` `fnv1a_32` `fnv1a_64`.
 
 ## JSON Parsing
 
diff --git a/docs/source/Tutorial.md b/docs/source/Tutorial.md
index 6f6ac9a..7d9c6d9 100644
--- a/docs/source/Tutorial.md
+++ b/docs/source/Tutorial.md
@@ -399,55 +399,56 @@
 
 Now we are ready to start building some buffers. In order to start, we need
 to create an instance of the `FlatBufferBuilder`, which will contain the buffer
-as it grows:
+as it grows. You can pass an initial size of the buffer (here 1024 bytes),
+which will grow automatically if needed:
 
 <div class="language-cpp">
 ~~~{.cpp}
   // Create a `FlatBufferBuilder`, which will be used to create our
   // monsters' FlatBuffers.
-  flatbuffers::FlatBufferBuilder builder;
+  flatbuffers::FlatBufferBuilder builder(1024);
 ~~~
 </div>
 <div class="language-java">
 ~~~{.java}
   // Create a `FlatBufferBuilder`, which will be used to create our
   // monsters' FlatBuffers.
-  FlatBufferBuilder builder = new FlatBufferBuilder(0);
+  FlatBufferBuilder builder = new FlatBufferBuilder(1024);
 ~~~
 </div>
 <div class="language-csharp">
 ~~~{.cs}
   // Create a `FlatBufferBuilder`, which will be used to create our
   // monsters' FlatBuffers.
-  var builder = new FlatBufferBuilder(1);
+  var builder = new FlatBufferBuilder(1024);
 ~~~
 </div>
 <div class="language-go">
 ~~~{.go}
   // Create a `FlatBufferBuilder`, which will be used to create our
   // monsters' FlatBuffers.
-  builder := flatbuffers.NewBuilder(0)
+  builder := flatbuffers.NewBuilder(1024)
 ~~~
 </div>
 <div class="language-python">
 ~~~{.py}
   # Create a `FlatBufferBuilder`, which will be used to create our
   # monsters' FlatBuffers.
-  builder = flatbuffers.Builder(0)
+  builder = flatbuffers.Builder(1024)
 ~~~
 </div>
 <div class="language-javascript">
 ~~~{.js}
   // Create a `flatbuffer.Builder`, which will be used to create our
   // monsters' FlatBuffers.
-  var builder = new flatbuffers.Builder(1);
+  var builder = new flatbuffers.Builder(1024);
 ~~~
 </div>
 <div class="language-php">
 ~~~{.php}
   // Create a `FlatBufferBuilder`, which will be used to create our
   // monsters' FlatBuffers.
-  $builder = new Google\FlatBuffers\FlatbufferBuilder(0);
+  $builder = new Google\FlatBuffers\FlatbufferBuilder(1024);
 ~~~
 </div>
 <div class="language-c">
@@ -727,8 +728,8 @@
   // Place the two weapons into an array, and pass it to the `createWeaponsVector()` method to
   // create a FlatBuffer vector.
   int[] weaps = new int[2];
-  weaps[1] = sword;
-  weaps[2] = axe;
+  weaps[0] = sword;
+  weaps[1] = axe;
 
   // Pass the `weaps` array into the `createWeaponsVector()` method to create a FlatBuffer vector.
   int weapons = Monster.createWeaponsVector(builder, weaps);
@@ -798,58 +799,6 @@
 there's also `CreateVectorOfStrings`.
 </div>
 
-To create a `struct`, use the `Vec3` class/struct that was generated by
-the schema compiler:
-
-<div class="language-cpp">
-~~~{.cpp}
-  // Create a `Vec3`, representing the Orc's position in 3-D space.
-  auto pos = Vec3(1.0f, 2.0f, 3.0f);
-~~~
-</div>
-<div class="language-java">
-~~~{.java}
-  // Create a `Vec3`, representing the Orc's position in 3-D space.
-  int pos = Vec3.createVec3(builder, 1.0f, 2.0f, 3.0f);
-~~~
-</div>
-<div class="language-csharp">
-~~~{.cs}
-  // Create a `Vec3`, representing the Orc's position in 3-D space.
-  var pos = Vec3.CreateVec3(builder, 1.0f, 2.0f, 3.0f);
-~~~
-</div>
-<div class="language-go">
-~~~{.go}
-  // Create a `Vec3`, representing the Orc's position in 3-D space.
-  pos := sample.CreateVec3(builder, 1.0, 2.0, 3.0)
-~~~
-</div>
-<div class="language-python">
-~~~{.py}
-  # Create a `Vec3`, representing the Orc's position in 3-D space.
-  pos = MyGame.Sample.Vec3.CreateVec3(builder, 1.0, 2.0, 3.0)
-~~~
-</div>
-<div class="language-javascript">
-~~~{.js}
-  // Create a `Vec3`, representing the Orc's position in 3-D space.
-  var pos = MyGame.Sample.Vec3.createVec3(builder, 1.0, 2.0, 3.0);
-~~~
-</div>
-<div class="language-php">
-~~~{.js}
-  // Create a `Vec3`, representing the Orc's position in 3-D space.
-  $pos = \MyGame\Sample\Vec3::CreateVec3($builder, 1.0, 2.0, 3.0);
-~~~
-</div>
-<div class="language-c">
-~~~{.c}
-  // Create a `Vec3`, representing the Orc's position in 3-D space.
-  ns(Vec3_t) pos = { 1.0f, 2.0f, 3.0f };
-~~~
-</div>
-
 We have now serialized the non-scalar components of the orc, so we
 can serialize the monster itself:
 
@@ -861,15 +810,16 @@
 
   // Finally, create the monster using the `CreateMonster` helper function
   // to set all fields.
-  auto orc = CreateMonster(builder, &pos, mana, hp, name, inventory, Color_Red,
-                           weapons, Equipment_Weapon, axe.Union());
+  auto orc = CreateMonster(builder, Vec3(1.0f, 2.0f, 3.0f), mana, hp, name,
+                           inventory, Color_Red, weapons, Equipment_Weapon,
+                           axe.Union());
 ~~~
 </div>
 <div class="language-java">
 ~~~{.java}
   // Create our monster using `startMonster()` and `endMonster()`.
   Monster.startMonster(builder);
-  Monster.addPos(builder, pos);
+  Monster.addPos(builder, Vec3.createVec3(builder, 1.0f, 2.0f, 3.0f));
   Monster.addName(builder, name);
   Monster.addColor(builder, Color.Red);
   Monster.addHp(builder, (short)300);
@@ -884,7 +834,7 @@
 ~~~{.cs}
   // Create our monster using `StartMonster()` and `EndMonster()`.
   Monster.StartMonster(builder);
-  Monster.AddPos(builder, pos);
+  Monster.AddPos(builder, Vec3.CreateVec3(builder, 1.0f, 2.0f, 3.0f));
   Monster.AddHp(builder, (short)300);
   Monster.AddName(builder, name);
   Monster.AddInventory(builder, inv);
@@ -899,7 +849,7 @@
 ~~~{.go}
   // Create our monster using `MonsterStart()` and `MonsterEnd()`.
   sample.MonsterStart(builder)
-  sample.MonsterAddPos(builder, pos)
+  sample.MonsterAddPos(builder, sample.CreateVec3(builder, 1.0, 2.0, 3.0))
   sample.MonsterAddHp(builder, 300)
   sample.MonsterAddName(builder, name)
   sample.MonsterAddInventory(builder, inv)
@@ -914,7 +864,8 @@
 ~~~{.py}
   # Create our monster by using `MonsterStart()` and `MonsterEnd()`.
   MyGame.Sample.Monster.MonsterStart(builder)
-  MyGame.Sample.Monster.MonsterAddPos(builder, pos)
+  MyGame.Sample.Monster.MonsterAddPos(builder,
+                          MyGame.Sample.Vec3.CreateVec3(builder, 1.0, 2.0, 3.0))
   MyGame.Sample.Monster.MonsterAddHp(builder, 300)
   MyGame.Sample.Monster.MonsterAddName(builder, name)
   MyGame.Sample.Monster.MonsterAddInventory(builder, inv)
@@ -931,7 +882,8 @@
 ~~~{.js}
   // Create our monster by using `startMonster()` and `endMonster()`.
   MyGame.Sample.Monster.startMonster(builder);
-  MyGame.Sample.Monster.addPos(builder, pos);
+  MyGame.Sample.Monster.addPos(builder,
+                         MyGame.Sample.Vec3.createVec3(builder, 1.0, 2.0, 3.0));
   MyGame.Sample.Monster.addHp(builder, 300);
   MyGame.Sample.Monster.addColor(builder, MyGame.Sample.Color.Red)
   MyGame.Sample.Monster.addName(builder, name);
@@ -946,7 +898,8 @@
 ~~~{.php}
   // Create our monster by using `StartMonster()` and `EndMonster()`.
   \MyGame\Sample\Monster::StartMonster($builder);
-  \MyGame\Sample\Monster::AddPos($builder, $pos);
+  \MyGame\Sample\Monster::AddPos($builder,
+                      \MyGame\Sample\Vec3::CreateVec3($builder, 1.0, 2.0, 3.0));
   \MyGame\Sample\Monster::AddHp($builder, 300);
   \MyGame\Sample\Monster::AddName($builder, $name);
   \MyGame\Sample\Monster::AddInventory($builder, $inv);
@@ -966,11 +919,21 @@
   // Define an equipment union. `create` calls in C has a single
   // argument for unions where C++ has both a type and a data argument.
   ns(Equipment_union_ref_t) equipped = ns(Equipment_as_Weapon(axe));
+  ns(Vec3_t) pos = { 1.0f, 2.0f, 3.0f };
   ns(Monster_create_as_root(B, &pos, mana, hp, name, inventory, ns(Color_Red),
           weapons, equipped));
 ~~~
 </div>
 
+Note how we create `Vec3` struct in-line in the table. Unlike tables, structs
+are simple combinations of scalars that are always stored inline, just like
+scalars themselves.
+
+**Important**: you should not nest tables or any other objects, which is why
+we created all the strings/vectors/tables that this monster refers to before
+`start`. If you try to create any of them between `start` and `end`, you
+will get an assert/exception/panic depending on your language.
+
 *Note: Since we are passing `150` as the `mana` field, which happens to be the
 default value, the field will not actually be written to the buffer, since the
 default value will be returned on query anyway. This is a nice space savings,
@@ -1161,12 +1124,23 @@
 ~~~{.java}
   // This must be called after `finish()`.
   java.nio.ByteBuffer buf = builder.dataBuffer();
+  // The data in this ByteBuffer does NOT start at 0, but at buf.position().
+  // The number of bytes is buf.remaining().
+
+  // Alternatively this copies the above data out of the ByteBuffer for you:
+  bytes[] buf = builder.sizedByteArray();
 ~~~
 </div>
 <div class="language-csharp">
 ~~~{.cs}
   // This must be called after `Finish()`.
   var buf = builder.DataBuffer; // Of type `FlatBuffers.ByteBuffer`.
+  // The data in this ByteBuffer does NOT start at 0, but at buf.Position.
+  // The end of the data is marked by buf.Length, so the size is
+  // buf.Length - buf.Position.
+
+  // Alternatively this copies the above data out of the ByteBuffer for you:
+  bytes[] buf = builder.SizedByteArray();
 ~~~
 </div>
 <div class="language-go">
@@ -1184,13 +1158,16 @@
 <div class="language-javascript">
 ~~~{.js}
   // This must be called after `finish()`.
-  var buf = builder.dataBuffer(); // Of type `flatbuffers.ByteBuffer`.
+  var buf = builder.asUint8Array(); // Of type `Uint8Array`.
 ~~~
 </div>
 <div class="language-php">
 ~~~{.php}
   // This must be called after `finish()`.
   $buf = $builder->dataBuffer(); // Of type `Google\FlatBuffers\ByteBuffer`
+  // The data in this ByteBuffer does NOT start at 0, but at buf->getPosition().
+  // The end of the data is marked by buf->capacity(), so the size is
+  // buf->capacity() - buf->getPosition().
 ~~~
 </div>
 <div class="language-c">
@@ -1217,6 +1194,11 @@
 ~~~
 </div>
 
+Now you can write the bytes to a file, send them over the network..
+**Make sure your file mode (or tranfer protocol) is set to BINARY, not text.**
+If you transfer a FlatBuffer in text mode, the buffer will be corrupted,
+which will lead to hard to find problems when you read the buffer.
+
 #### Reading Orc FlatBuffers
 
 Now that we have successfully created an `Orc` FlatBuffer, the monster data can
@@ -1312,92 +1294,82 @@
 ~~~
 </div>
 
-Then, assuming you have a variable containing to the bytes of data from disk,
-network, etc., you can create a monster from this data:
+Then, assuming you have a buffer of bytes received from disk,
+network, etc., you can create start accessing the buffer like so:
+
+**Again, make sure you read the bytes in BINARY mode, otherwise the code below
+won't work**
 
 <div class="language-cpp">
 ~~~{.cpp}
-  // We can access the buffer we just made directly. Pretend this came over a
-  // network, was read off of disk, etc.
-  auto buffer_pointer = builder.GetBufferPointer();
+  uint8_t *buffer_pointer = /* the data you just read */;
 
-  // Deserialize the data from the buffer.
+  // Get a pointer to the root object inside the buffer.
   auto monster = GetMonster(buffer_pointer);
 
-  // `monster` is of type`Monster *`, and points to somewhere inside the buffer.
-
+  // `monster` is of type `Monster *`.
   // Note: root object pointers are NOT the same as `buffer_pointer`.
 ~~~
 </div>
 <div class="language-java">
 ~~~{.java}
-  // We can access the buffer we just made directly. Pretend this came over a
-  // network, was read off of disk, etc.
-  java.nio.ByteBuffer buf = builder.dataBuffer();
+  byte[] bytes = /* the data you just read */
+  java.nio.ByteBuffer buf = java.nio.ByteBuffer.wrap(bytes);
 
-  // Deserialize the data from the buffer.
+  // Get an accessor to the root object inside the buffer.
   Monster monster = Monster.getRootAsMonster(buf);
 ~~~
 </div>
 <div class="language-csharp">
 ~~~{.cs}
-  // We can access the buffer we just made directly. Pretend this came over a
-  // network, was read off of disk, etc.
-  var buf = builder.DataBuffer;
+  byte[] bytes = /* the data you just read */
+  var buf = new ByteBuffer(bytes);
 
-  // Deserialize the data from the buffer.
+  // Get an accessor to the root object inside the buffer.
   var monster = Monster.GetRootAsMonster(buf);
 ~~~
 </div>
 <div class="language-go">
 ~~~{.go}
-  // We can access the buffer we just made directly. Pretend this came over a
-  // network, was read off of disk, etc.
-  buf := builder.FinishedBytes()
+  var buf []byte = /* the data you just read */
 
-  // Deserialize the data from the buffer.
+  // Get an accessor to the root object inside the buffer.
   monster := sample.GetRootAsMonster(buf, 0)
 
-  // Note: We use `0` for the offset here, since we got the data using the
-  // `builder.FinishedBytes()` method. This simulates the data you would
-  // store/receive in your FlatBuffer. If you wanted to read from the
-  // `builder.Bytes` directly, you would need to pass in the offset of
-  // `builder.Head()`, as the builder actually constructs the buffer backwards.
+  // Note: We use `0` for the offset here, which is typical for most buffers
+  // you would read. If you wanted to read from `builder.Bytes` directly, you
+  // would need to pass in the offset of `builder.Head()`, as the builder
+  // constructs the buffer backwards, so may not start at offset 0.
 ~~~
 </div>
 <div class="language-python">
 ~~~{.py}
-  # We can access the buffer we just made directly. Pretend this came over a
-  # network, was read off of disk, etc.
-  buf = builder.Output()
+  buf = /* the data you just read, in an object of type "bytearray" */
 
-  # Deserialize the data from the buffer.
+  // Get an accessor to the root object inside the buffer.
   monster = MyGame.Sample.Monster.Monster.GetRootAsMonster(buf, 0)
 
-  # Note: We use `0` for the offset here, since we got the data using the
-  # `builder.Output()` method. This simulates the data you would store/receive
-  # in your FlatBuffer. If you wanted to read from the `builder.Bytes` directly,
+  # Note: We use `0` for the offset here, which is typical for most buffers
+  # you would read.  If you wanted to read from the `builder.Bytes` directly,
   # you would need to pass in the offset of `builder.Head()`, as the builder
-  # actually constructs the buffer backwards.
+  # constructs the buffer backwards, so may not start at offset 0.
 ~~~
 </div>
 <div class="language-javascript">
 ~~~{.js}
-  // We can access the buffer we just made directly. Pretend this came over a
-  // network, was read off of disk, etc.
-  var buf = builder.dataBuffer();
+  var bytes = /* the data you just read, in an object of type "Uint8Array" */
+  var buf = new flatbuffers.ByteBuffer(bytes);
 
-  // Deserialize the data from the buffer.
+  // Get an accessor to the root object inside the buffer.
   var monster = MyGame.Sample.Monster.getRootAsMonster(buf);
 ~~~
 </div>
 <div class="language-php">
 ~~~{.php}
-  // We can access the buffer we just made directly. Pretend this came over a
-  // network, was read off of disk, etc.
-  $buf = $builder->dataBuffer();
+  $bytes = /* the data you just read, in a string */
+  $buf = Google\FlatBuffers\ByteBuffer::wrap($bytes);
 
-  // Deserialize the data from the buffer.
+  // Get an accessor to the root object inside the buffer.
   $monster = \MyGame\Sample\Monster::GetRootAsMonster($buf);
 ~~~
 </div>
@@ -1881,6 +1853,9 @@
 force all fields you set to actually be written. This, of course, increases the
 size of the buffer somewhat, but this may be acceptable for a mutable buffer.
 
+If this is not sufficient, other ways of mutating FlatBuffers may be supported
+in your language through an object based API (`--gen-object-api`) or reflection.
+See the individual language documents for support.
 
 ## JSON with FlatBuffers
 
diff --git a/docs/source/doxyfile b/docs/source/doxyfile
index bef63f5..db3eeac 100755
--- a/docs/source/doxyfile
+++ b/docs/source/doxyfile
@@ -761,7 +761,7 @@
         "WhitePaper.md" \
         "Internals.md" \
         "Grammar.md" \
-        "CONTRIBUTING.md" \
+        "../../CONTRIBUTING.md" \
         "Tutorial.md" \
         "GoApi.md" \
         "groups" \
diff --git a/go/grpc.go b/go/grpc.go
new file mode 100644
index 0000000..07d374b
--- /dev/null
+++ b/go/grpc.go
@@ -0,0 +1,23 @@
+package flatbuffers
+
+// FlatbuffersCodec implements gRPC-go Codec which is used to encode and decode messages.
+var Codec string = "flatbuffers"
+
+type FlatbuffersCodec struct{}
+
+func (FlatbuffersCodec) Marshal(v interface{}) ([]byte, error) {
+	return v.(*Builder).FinishedBytes(), nil
+}
+
+func (FlatbuffersCodec) Unmarshal(data []byte, v interface{}) error {
+	v.(flatbuffersInit).Init(data, GetUOffsetT(data))
+	return nil
+}
+
+func (FlatbuffersCodec) String() string {
+	return Codec
+}
+
+type flatbuffersInit interface {
+	Init(data []byte, i UOffsetT)
+}
diff --git a/go/lib.go b/go/lib.go
new file mode 100644
index 0000000..adfce52
--- /dev/null
+++ b/go/lib.go
@@ -0,0 +1,13 @@
+package flatbuffers
+
+// FlatBuffer is the interface that represents a flatbuffer.
+type FlatBuffer interface {
+	Table() Table
+	Init(buf []byte, i UOffsetT)
+}
+
+// GetRootAs is a generic helper to initialize a FlatBuffer with the provided buffer bytes and its data offset.
+func GetRootAs(buf []byte, offset UOffsetT, fb FlatBuffer) {
+	n := GetUOffsetT(buf[offset:])
+	fb.Init(buf, n+offset)
+}
diff --git a/go/table.go b/go/table.go
index 976a7db..01d3db1 100644
--- a/go/table.go
+++ b/go/table.go
@@ -293,3 +293,213 @@
 	}
 	return VOffsetT(off)
 }
+
+// MutateBool updates a bool at the given offset.
+func (t *Table) MutateBool(off UOffsetT, n bool) bool {
+	WriteBool(t.Bytes[off:], n)
+	return true
+}
+
+// MutateByte updates a Byte at the given offset.
+func (t *Table) MutateByte(off UOffsetT, n byte) bool {
+	WriteByte(t.Bytes[off:], n)
+	return true
+}
+
+// MutateUint8 updates a Uint8 at the given offset.
+func (t *Table) MutateUint8(off UOffsetT, n uint8) bool {
+	WriteUint8(t.Bytes[off:], n)
+	return true
+}
+
+// MutateUint16 updates a Uint16 at the given offset.
+func (t *Table) MutateUint16(off UOffsetT, n uint16) bool {
+	WriteUint16(t.Bytes[off:], n)
+	return true
+}
+
+// MutateUint32 updates a Uint32 at the given offset.
+func (t *Table) MutateUint32(off UOffsetT, n uint32) bool {
+	WriteUint32(t.Bytes[off:], n)
+	return true
+}
+
+// MutateUint64 updates a Uint64 at the given offset.
+func (t *Table) MutateUint64(off UOffsetT, n uint64) bool {
+	WriteUint64(t.Bytes[off:], n)
+	return true
+}
+
+// MutateInt8 updates a Int8 at the given offset.
+func (t *Table) MutateInt8(off UOffsetT, n int8) bool {
+	WriteInt8(t.Bytes[off:], n)
+	return true
+}
+
+// MutateInt16 updates a Int16 at the given offset.
+func (t *Table) MutateInt16(off UOffsetT, n int16) bool {
+	WriteInt16(t.Bytes[off:], n)
+	return true
+}
+
+// MutateInt32 updates a Int32 at the given offset.
+func (t *Table) MutateInt32(off UOffsetT, n int32) bool {
+	WriteInt32(t.Bytes[off:], n)
+	return true
+}
+
+// MutateInt64 updates a Int64 at the given offset.
+func (t *Table) MutateInt64(off UOffsetT, n int64) bool {
+	WriteInt64(t.Bytes[off:], n)
+	return true
+}
+
+// MutateFloat32 updates a Float32 at the given offset.
+func (t *Table) MutateFloat32(off UOffsetT, n float32) bool {
+	WriteFloat32(t.Bytes[off:], n)
+	return true
+}
+
+// MutateFloat64 updates a Float64 at the given offset.
+func (t *Table) MutateFloat64(off UOffsetT, n float64) bool {
+	WriteFloat64(t.Bytes[off:], n)
+	return true
+}
+
+// MutateUOffsetT updates a UOffsetT at the given offset.
+func (t *Table) MutateUOffsetT(off UOffsetT, n UOffsetT) bool {
+	WriteUOffsetT(t.Bytes[off:], n)
+	return true
+}
+
+// MutateVOffsetT updates a VOffsetT at the given offset.
+func (t *Table) MutateVOffsetT(off UOffsetT, n VOffsetT) bool {
+	WriteVOffsetT(t.Bytes[off:], n)
+	return true
+}
+
+// MutateSOffsetT updates a SOffsetT at the given offset.
+func (t *Table) MutateSOffsetT(off UOffsetT, n SOffsetT) bool {
+	WriteSOffsetT(t.Bytes[off:], n)
+	return true
+}
+
+// MutateBoolSlot updates the bool at given vtable location
+func (t *Table) MutateBoolSlot(slot VOffsetT, n bool) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateBool(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateByteSlot updates the byte at given vtable location
+func (t *Table) MutateByteSlot(slot VOffsetT, n byte) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateByte(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateInt8Slot updates the int8 at given vtable location
+func (t *Table) MutateInt8Slot(slot VOffsetT, n int8) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateInt8(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateUint8Slot updates the uint8 at given vtable location
+func (t *Table) MutateUint8Slot(slot VOffsetT, n uint8) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateUint8(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateInt16Slot updates the int16 at given vtable location
+func (t *Table) MutateInt16Slot(slot VOffsetT, n int16) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateInt16(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateUint16Slot updates the uint16 at given vtable location
+func (t *Table) MutateUint16Slot(slot VOffsetT, n uint16) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateUint16(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateInt32Slot updates the int32 at given vtable location
+func (t *Table) MutateInt32Slot(slot VOffsetT, n int32) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateInt32(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateUint32Slot updates the uint32 at given vtable location
+func (t *Table) MutateUint32Slot(slot VOffsetT, n uint32) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateUint32(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateInt64Slot updates the int64 at given vtable location
+func (t *Table) MutateInt64Slot(slot VOffsetT, n int64) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateInt64(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateUint64Slot updates the uint64 at given vtable location
+func (t *Table) MutateUint64Slot(slot VOffsetT, n uint64) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateUint64(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateFloat32Slot updates the float32 at given vtable location
+func (t *Table) MutateFloat32Slot(slot VOffsetT, n float32) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateFloat32(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
+
+// MutateFloat64Slot updates the float64 at given vtable location
+func (t *Table) MutateFloat64Slot(slot VOffsetT, n float64) bool {
+	if off := t.Offset(slot); off != 0 {
+		t.MutateFloat64(t.Pos+UOffsetT(off), n)
+		return true
+	}
+
+	return false
+}
diff --git a/grpc/src/compiler/cpp_generator.cc b/grpc/src/compiler/cpp_generator.cc
index 9319c41..e8ad49e 100644
--- a/grpc/src/compiler/cpp_generator.cc
+++ b/grpc/src/compiler/cpp_generator.cc
@@ -67,7 +67,8 @@
 template<class T, size_t N>
 T *array_end(T (&array)[N]) { return array + N; }
 
-void PrintIncludes(Printer *printer, const std::vector<grpc::string>& headers, const Parameters &params) {
+void PrintIncludes(grpc_generator::Printer *printer, 
+                   const std::vector<grpc::string>& headers, const Parameters &params) {
   std::map<grpc::string, grpc::string> vars;
 
   vars["l"] = params.use_system_headers ? '<' : '"';
@@ -86,7 +87,7 @@
   }
 }
 
-grpc::string GetHeaderPrologue(File *file, const Parameters & /*params*/) {
+grpc::string GetHeaderPrologue(grpc_generator::File *file, const Parameters & /*params*/) {
   grpc::string output;
   {
     // Scope the output stream so it closes and finalizes output to the string.
@@ -111,7 +112,7 @@
   return output;
 }
 
-grpc::string GetHeaderIncludes(File *file,
+grpc::string GetHeaderIncludes(grpc_generator::File *file,
                                const Parameters &params) {
   grpc::string output;
   {
@@ -154,7 +155,7 @@
 }
 
 void PrintHeaderClientMethodInterfaces(
-    Printer *printer, const Method *method,
+    grpc_generator::Printer *printer, const grpc_generator::Method *method,
     std::map<grpc::string, grpc::string> *vars, bool is_public) {
   (*vars)["Method"] = method->name();
   (*vars)["Request"] = method->input_type_name();
@@ -303,8 +304,8 @@
   }
 }
 
-void PrintHeaderClientMethod(Printer *printer,
-                             const Method *method,
+void PrintHeaderClientMethod(grpc_generator::Printer *printer,
+                             const grpc_generator::Method *method,
                              std::map<grpc::string, grpc::string> *vars,
                              bool is_public) {
   (*vars)["Method"] = method->name();
@@ -445,13 +446,13 @@
   }
 }
 
-void PrintHeaderClientMethodData(Printer *printer, const Method *method,
+void PrintHeaderClientMethodData(grpc_generator::Printer *printer, const grpc_generator::Method *method,
                                  std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Method"] = method->name();
   printer->Print(*vars, "const ::grpc::RpcMethod rpcmethod_$Method$_;\n");
 }
 
-void PrintHeaderServerMethodSync(Printer *printer, const Method *method,
+void PrintHeaderServerMethodSync(grpc_generator::Printer *printer, const grpc_generator::Method *method,
                                  std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Method"] = method->name();
   (*vars)["Request"] = method->input_type_name();
@@ -483,8 +484,8 @@
 }
 
 void PrintHeaderServerMethodAsync(
-    Printer *printer,
-    const Method *method,
+    grpc_generator::Printer *printer,
+    const grpc_generator::Method *method,
     std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Method"] = method->name();
   (*vars)["Request"] = method->input_type_name();
@@ -599,8 +600,8 @@
 }
 
 void PrintHeaderServerMethodGeneric(
-    Printer *printer,
-    const Method *method,
+    grpc_generator::Printer *printer,
+    const grpc_generator::Method *method,
     std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Method"] = method->name();
   (*vars)["Request"] = method->input_type_name();
@@ -669,8 +670,8 @@
   printer->Print(*vars, "};\n");
 }
 
-void PrintHeaderService(Printer *printer,
-                        const Service *service,
+void PrintHeaderService(grpc_generator::Printer *printer,
+                        const grpc_generator::Service *service,
                         std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Service"] = service->name();
 
@@ -764,7 +765,7 @@
   printer->Print("};\n");
 }
 
-grpc::string GetHeaderServices(File *file,
+grpc::string GetHeaderServices(grpc_generator::File *file,
                                const Parameters &params) {
   grpc::string output;
   {
@@ -795,7 +796,7 @@
   return output;
 }
 
-grpc::string GetHeaderEpilogue(File *file, const Parameters & /*params*/) {
+grpc::string GetHeaderEpilogue(grpc_generator::File *file, const Parameters & /*params*/) {
   grpc::string output;
   {
     // Scope the output stream so it closes and finalizes output to the string.
@@ -821,7 +822,7 @@
   return output;
 }
 
-grpc::string GetSourcePrologue(File *file, const Parameters & /*params*/) {
+grpc::string GetSourcePrologue(grpc_generator::File *file, const Parameters & /*params*/) {
   grpc::string output;
   {
     // Scope the output stream so it closes and finalizes output to the string.
@@ -845,7 +846,7 @@
   return output;
 }
 
-grpc::string GetSourceIncludes(File *file,
+grpc::string GetSourceIncludes(grpc_generator::File *file,
                                const Parameters &params) {
   grpc::string output;
   {
@@ -880,8 +881,8 @@
   return output;
 }
 
-void PrintSourceClientMethod(Printer *printer,
-                             const Method *method,
+void PrintSourceClientMethod(grpc_generator::Printer *printer,
+                             const grpc_generator::Method *method,
                              std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Method"] = method->name();
   (*vars)["Request"] = method->input_type_name();
@@ -981,8 +982,8 @@
   }
 }
 
-void PrintSourceServerMethod(Printer *printer,
-                             const Method *method,
+void PrintSourceServerMethod(grpc_generator::Printer *printer,
+                             const grpc_generator::Method *method,
                              std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Method"] = method->name();
   (*vars)["Request"] = method->input_type_name();
@@ -1040,8 +1041,8 @@
   }
 }
 
-void PrintSourceService(Printer *printer,
-                        const Service *service,
+void PrintSourceService(grpc_generator::Printer *printer,
+                        const grpc_generator::Service *service,
                         std::map<grpc::string, grpc::string> *vars) {
   (*vars)["Service"] = service->name();
 
@@ -1153,7 +1154,7 @@
   }
 }
 
-grpc::string GetSourceServices(File *file,
+grpc::string GetSourceServices(grpc_generator::File *file,
                                const Parameters &params) {
   grpc::string output;
   {
@@ -1182,7 +1183,7 @@
   return output;
 }
 
-grpc::string GetSourceEpilogue(File *file, const Parameters & /*params*/) {
+grpc::string GetSourceEpilogue(grpc_generator::File *file, const Parameters & /*params*/) {
   grpc::string temp;
 
   if (!file->package().empty()) {
diff --git a/grpc/src/compiler/cpp_generator.h b/grpc/src/compiler/cpp_generator.h
index 953ddfd..a4adee7 100644
--- a/grpc/src/compiler/cpp_generator.h
+++ b/grpc/src/compiler/cpp_generator.h
@@ -41,16 +41,7 @@
 #include <memory>
 #include <vector>
 
-#ifndef GRPC_CUSTOM_STRING
-#include <string>
-#define GRPC_CUSTOM_STRING std::string
-#endif
-
-namespace grpc {
-
-typedef GRPC_CUSTOM_STRING string;
-
-}  // namespace grpc
+#include "src/compiler/schema_interface.h"
 
 namespace grpc_cpp_generator {
 
@@ -64,83 +55,29 @@
   grpc::string grpc_search_path;
 };
 
-// An abstract interface representing a method.
-struct Method {
-  virtual ~Method() {}
-
-  virtual grpc::string name() const = 0;
-
-  virtual grpc::string input_type_name() const = 0;
-  virtual grpc::string output_type_name() const = 0;
-
-  virtual bool NoStreaming() const = 0;
-  virtual bool ClientOnlyStreaming() const = 0;
-  virtual bool ServerOnlyStreaming() const = 0;
-  virtual bool BidiStreaming() const = 0;
-};
-
-// An abstract interface representing a service.
-struct Service {
-  virtual ~Service() {}
-
-  virtual grpc::string name() const = 0;
-
-  virtual int method_count() const = 0;
-  virtual std::unique_ptr<const Method> method(int i) const = 0;
-};
-
-struct Printer {
-  virtual ~Printer() {}
-
-  virtual void Print(const std::map<grpc::string, grpc::string> &vars,
-                     const char *template_string) = 0;
-  virtual void Print(const char *string) = 0;
-  virtual void Indent() = 0;
-  virtual void Outdent() = 0;
-};
-
-// An interface that allows the source generated to be output using various
-// libraries/idls/serializers.
-struct File {
-  virtual ~File() {}
-
-  virtual grpc::string filename() const = 0;
-  virtual grpc::string filename_without_ext() const = 0;
-  virtual grpc::string message_header_ext() const = 0;
-  virtual grpc::string service_header_ext() const = 0;
-  virtual grpc::string package() const = 0;
-  virtual std::vector<grpc::string> package_parts() const = 0;
-  virtual grpc::string additional_headers() const = 0;
-
-  virtual int service_count() const = 0;
-  virtual std::unique_ptr<const Service> service(int i) const = 0;
-
-  virtual std::unique_ptr<Printer> CreatePrinter(grpc::string *str) const = 0;
-};
-
 // Return the prologue of the generated header file.
-grpc::string GetHeaderPrologue(File *file, const Parameters &params);
+grpc::string GetHeaderPrologue(grpc_generator::File *file, const Parameters &params);
 
 // Return the includes needed for generated header file.
-grpc::string GetHeaderIncludes(File *file, const Parameters &params);
+grpc::string GetHeaderIncludes(grpc_generator::File *file, const Parameters &params);
 
 // Return the includes needed for generated source file.
-grpc::string GetSourceIncludes(File *file, const Parameters &params);
+grpc::string GetSourceIncludes(grpc_generator::File *file, const Parameters &params);
 
 // Return the epilogue of the generated header file.
-grpc::string GetHeaderEpilogue(File *file, const Parameters &params);
+grpc::string GetHeaderEpilogue(grpc_generator::File *file, const Parameters &params);
 
 // Return the prologue of the generated source file.
-grpc::string GetSourcePrologue(File *file, const Parameters &params);
+grpc::string GetSourcePrologue(grpc_generator::File *file, const Parameters &params);
 
 // Return the services for generated header file.
-grpc::string GetHeaderServices(File *file, const Parameters &params);
+grpc::string GetHeaderServices(grpc_generator::File *file, const Parameters &params);
 
 // Return the services for generated source file.
-grpc::string GetSourceServices(File *file, const Parameters &params);
+grpc::string GetSourceServices(grpc_generator::File *file, const Parameters &params);
 
 // Return the epilogue of the generated source file.
-grpc::string GetSourceEpilogue(File *file, const Parameters &params);
+grpc::string GetSourceEpilogue(grpc_generator::File *file, const Parameters &params);
 
 }  // namespace grpc_cpp_generator
 
diff --git a/grpc/src/compiler/go_generator.cc b/grpc/src/compiler/go_generator.cc
new file mode 100644
index 0000000..a35e572
--- /dev/null
+++ b/grpc/src/compiler/go_generator.cc
@@ -0,0 +1,437 @@
+/*
+ *
+ * Copyright 2015, Google Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation AN/or other materials provided with the
+ * distribution.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+
+#include <map>
+#include <cctype>
+#include <sstream>
+
+#include "src/compiler/go_generator.h"
+
+template <class T>
+grpc::string as_string(T x) {
+	std::ostringstream out;
+	out << x;
+	return out.str();
+}
+
+namespace grpc_go_generator {
+
+// Returns string with first letter to lowerCase
+grpc::string unexportName(grpc::string s) {
+	if (s.size() <= 0)
+		return s;
+	s[0] = std::tolower(s[0]);
+	return s;
+}
+
+// Returns string with first letter to uppercase
+grpc::string exportName(grpc::string s) {
+	if (s.size() <= 0)
+		return s;
+	s[0] = std::toupper(s[0]);
+	return s;
+}
+
+// Generates imports for the service
+void GenerateImports(grpc_generator::File *file, grpc_generator::Printer *printer,
+                     std::map<grpc::string, grpc::string> vars) {
+	vars["filename"] = file->filename();
+	printer->Print("//Generated by gRPC Go plugin\n");
+	printer->Print("//If you make any local changes, they will be lost\n");
+	printer->Print(vars, "//source: $filename$\n\n");
+	printer->Print(vars, "package $Package$\n\n");
+	if (file->additional_imports() != "") {
+		printer->Print(file->additional_imports().c_str());
+		printer->Print("\n\n");
+	}
+	printer->Print("import (\n");
+	printer->Indent();
+	printer->Print(vars, "$context$ \"golang.org/x/net/context\"\n");
+	printer->Print(vars, "$grpc$ \"google.golang.org/grpc\"\n");
+	printer->Outdent();
+	printer->Print(")\n\n");
+}
+
+// Generates Server method signature source
+void GenerateServerMethodSignature(const grpc_generator::Method *method, grpc_generator::Printer *printer,
+                                   std::map<grpc::string, grpc::string> vars) {
+	vars["Method"] = exportName(method->name());
+	vars["Request"] = method->input_name();
+	vars["Response"] = (vars["CustomMethodIO"] == "") ? method->output_name() : vars["CustomMethodIO"];
+	if (method->NoStreaming()) {
+		printer->Print(vars, "$Method$($context$.Context, *$Request$) (*$Response$, error)");
+	} else if (method->ServerOnlyStreaming()) {
+		printer->Print(vars, "$Method$(*$Request$, $Service$_$Method$Server) error");
+	} else {
+		printer->Print(vars, "$Method$($Service$_$Method$Server) error");
+	}
+}
+
+void GenerateServerMethod(const grpc_generator::Method *method, grpc_generator::Printer *printer,
+                          std::map<grpc::string, grpc::string> vars) {
+	vars["Method"] = exportName(method->name());
+	vars["Request"] = method->input_name();
+	vars["Response"] = (vars["CustomMethodIO"] == "") ? method->output_name() : vars["CustomMethodIO"];
+	vars["FullMethodName"] = "/" + vars["Package"] + "." + vars["Service"] + "/" + vars["Method"];
+	vars["Handler"] = "_" + vars["Service"] + "_" + vars["Method"] + "_Handler";
+	if (method->NoStreaming()) {
+		printer->Print(vars, "func $Handler$(srv interface{}, ctx $context$.Context,\n\tdec func(interface{}) error, interceptor $grpc$.UnaryServerInterceptor) (interface{}, error) {\n");
+		printer->Indent();
+		printer->Print(vars, "in := new($Request$)\n");
+		printer->Print("if err := dec(in); err != nil { return nil, err }\n");
+		printer->Print(vars, "if interceptor == nil { return srv.($Service$Server).$Method$(ctx, in) }\n");
+		printer->Print(vars, "info := &$grpc$.UnaryServerInfo{\n");
+		printer->Indent();
+		printer->Print("Server: srv,\n");
+		printer->Print(vars, "FullMethod: \"$FullMethodName$\",\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+		printer->Print(vars, "handler := func(ctx $context$.Context, req interface{}) (interface{}, error) {\n");
+		printer->Indent();
+		printer->Print(vars, "return srv.($Service$Server).$Method$(ctx, req.(* $Request$))\n");
+		printer->Outdent();
+		printer->Print("}\n");
+		printer->Print("return interceptor(ctx, in, info, handler)\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+		return;
+	}
+	vars["StreamType"] = vars["ServiceUnexported"] + vars["Method"] + "Server";
+	printer->Print(vars, "func $Handler$(srv interface{}, stream $grpc$.ServerStream) error {\n");
+	printer->Indent();
+	if (method->ServerOnlyStreaming()) {
+		printer->Print(vars, "m := new($Request$)\n");
+		printer->Print(vars, "if err := stream.RecvMsg(m); err != nil { return err }\n");
+		printer->Print(vars, "return srv.($Service$Server).$Method$(m, &$StreamType${stream})\n");
+	} else {
+		printer->Print(vars, "return srv.($Service$Server).$Method$(&$StreamType${stream})\n");
+	}
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	bool genSend = method->BidiStreaming() || method->ServerOnlyStreaming();
+	bool genRecv = method->BidiStreaming() || method->ClientOnlyStreaming();
+	bool genSendAndClose = method->ClientOnlyStreaming();
+
+	printer->Print(vars, "type $Service$_$Method$Server interface { \n");
+	printer->Indent();
+	if (genSend) {
+		printer->Print(vars, "Send(* $Response$) error\n");
+	}
+	if (genRecv) {
+		printer->Print(vars, "Recv() (* $Request$, error)\n");
+	}
+	if (genSendAndClose) {
+		printer->Print(vars, "SendAndClose(* $Response$) error\n");
+	}
+	printer->Print(vars, "$grpc$.ServerStream\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	printer->Print(vars, "type $StreamType$ struct {\n");
+	printer->Indent();
+	printer->Print(vars, "$grpc$.ServerStream\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	if (genSend) {
+		printer->Print(vars, "func (x *$StreamType$) Send(m *$Response$) error {\n");
+		printer->Indent();
+		printer->Print("return x.ServerStream.SendMsg(m)\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+	}
+	if (genRecv) {
+		printer->Print(vars, "func (x *$StreamType$) Recv() (*$Request$, error) {\n");
+		printer->Indent();
+		printer->Print(vars, "m := new($Request$)\n");
+		printer->Print("if err := x.ServerStream.RecvMsg(m); err != nil { return nil, err }\n");
+		printer->Print("return m, nil\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+	}
+	if (genSendAndClose) {
+		printer->Print(vars, "func (x *$StreamType$) SendAndClose(m *$Response$) error {\n");
+		printer->Indent();
+		printer->Print("return x.ServerStream.SendMsg(m)\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+	}
+
+}
+
+// Generates Client method signature source
+void GenerateClientMethodSignature(const grpc_generator::Method *method, grpc_generator::Printer *printer,
+                                   std::map<grpc::string, grpc::string> vars) {
+	vars["Method"] = exportName(method->name());
+	vars["Request"] = ", in *" + ((vars["CustomMethodIO"] == "") ? method->input_name() : vars["CustomMethodIO"]);
+	if (method->ClientOnlyStreaming() || method->BidiStreaming()) {
+		vars["Request"] = "";
+	}
+	vars["Response"] = "* " + method->output_name();
+	if (method->ClientOnlyStreaming() || method->BidiStreaming() || method->ServerOnlyStreaming()) {
+		vars["Response"] = vars["Service"] + "_" + vars["Method"] + "Client" ;
+	}
+	printer->Print(vars, "$Method$(ctx $context$.Context$Request$, \n\topts... $grpc$.CallOption) ($Response$, error)");
+}
+
+// Generates Client method source
+void GenerateClientMethod(const grpc_generator::Method *method, grpc_generator::Printer *printer,
+                          std::map<grpc::string, grpc::string> vars) {
+	printer->Print(vars, "func (c *$ServiceUnexported$Client) ");
+	GenerateClientMethodSignature(method, printer, vars);
+	printer->Print(" {\n");
+	printer->Indent();
+	vars["Method"] = exportName(method->name());
+	vars["Request"] = (vars["CustomMethodIO"] == "") ? method->input_name() : vars["CustomMethodIO"];
+	vars["Response"] = method->output_name();
+	vars["FullMethodName"] = "/" + vars["Package"] + "." + vars["Service"] + "/" + vars["Method"];
+	if (method->NoStreaming()) {
+		printer->Print(vars, "out := new($Response$)\n");
+		printer->Print(vars, "err := $grpc$.Invoke(ctx, \"$FullMethodName$\", in, out, c.cc, opts...)\n");
+		printer->Print("if err != nil { return nil, err }\n");
+		printer->Print("return out, nil\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+		return;
+	}
+	vars["StreamType"] = vars["ServiceUnexported"] + vars["Method"] + "Client";
+	printer->Print(vars, "stream, err := $grpc$.NewClientStream(ctx, &$MethodDesc$, c.cc, \"$FullMethodName$\", opts...)\n");
+	printer->Print("if err != nil { return nil, err }\n");
+
+	printer->Print(vars, "x := &$StreamType${stream}\n");
+	if (method->ServerOnlyStreaming()) {
+		printer->Print("if err := x.ClientStream.SendMsg(in); err != nil { return nil, err }\n");
+		printer->Print("if err := x.ClientStream.CloseSend(); err != nil { return nil, err }\n");
+	}
+	printer->Print("return x,nil\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	bool genSend = method->BidiStreaming() || method->ClientOnlyStreaming();
+	bool genRecv = method->BidiStreaming() || method->ServerOnlyStreaming();
+	bool genCloseAndRecv = method->ClientOnlyStreaming();
+
+	//Stream interface
+	printer->Print(vars, "type $Service$_$Method$Client interface {\n");
+	printer->Indent();
+	if (genSend) {
+		printer->Print(vars, "Send(*$Request$) error\n");
+	}
+	if (genRecv) {
+		printer->Print(vars, "Recv() (*$Response$, error)\n");
+	}
+	if (genCloseAndRecv) {
+		printer->Print(vars, "CloseAndRecv() (*$Response$, error)\n");
+	}
+	printer->Print(vars, "$grpc$.ClientStream\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	//Stream Client
+	printer->Print(vars, "type $StreamType$ struct{\n");
+	printer->Indent();
+	printer->Print(vars, "$grpc$.ClientStream\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	if (genSend) {
+		printer->Print(vars, "func (x *$StreamType$) Send(m *$Request$) error {\n");
+		printer->Indent();
+		printer->Print("return x.ClientStream.SendMsg(m)\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+	}
+
+	if (genRecv) {
+		printer->Print(vars, "func (x *$StreamType$) Recv() (*$Response$, error) {\n");
+		printer->Indent();
+		printer->Print(vars, "m := new($Response$)\n");
+		printer->Print("if err := x.ClientStream.RecvMsg(m); err != nil { return nil, err }\n");
+		printer->Print("return m, nil\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+	}
+
+	if (genCloseAndRecv) {
+		printer->Print(vars, "func (x *$StreamType$) CloseAndRecv() (*$Response$, error) {\n");
+		printer->Indent();
+		printer->Print("if err := x.ClientStream.CloseSend(); err != nil { return nil, err }\n");
+		printer->Print(vars, "m := new ($Response$)\n");
+		printer->Print("if err := x.ClientStream.RecvMsg(m); err != nil { return nil, err }\n");
+		printer->Print("return m, nil\n");
+		printer->Outdent();
+		printer->Print("}\n\n");
+	}
+}
+
+// Generates client API for the service
+void GenerateService(const grpc_generator::Service *service, grpc_generator::Printer* printer,
+                     std::map<grpc::string, grpc::string> vars) {
+	vars["Service"] = exportName(service->name());
+	// Client Interface
+	printer->Print(vars, "// Client API for $Service$ service\n");
+	printer->Print(vars, "type $Service$Client interface{\n");
+	printer->Indent();
+	for (int i = 0; i < service->method_count(); i++) {
+		GenerateClientMethodSignature(service->method(i).get(), printer, vars);
+		printer->Print("\n");
+	}
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	// Client structure
+	vars["ServiceUnexported"] = unexportName(vars["Service"]);
+	printer->Print(vars, "type $ServiceUnexported$Client struct {\n");
+	printer->Indent();
+	printer->Print(vars, "cc *$grpc$.ClientConn\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	// NewClient
+	printer->Print(vars, "func New$Service$Client(cc *$grpc$.ClientConn) $Service$Client {\n");
+	printer->Indent();
+	printer->Print(vars, "return &$ServiceUnexported$Client{cc}");
+	printer->Outdent();
+	printer->Print("\n}\n\n");
+
+	int unary_methods = 0, streaming_methods = 0;
+	vars["ServiceDesc"] = "_" + vars["Service"] + "_serviceDesc";
+	for (int i = 0; i < service->method_count(); i++) {
+		auto method = service->method(i);
+		if (method->NoStreaming()) {
+			vars["MethodDesc"] = vars["ServiceDesc"] + ".Method[" + as_string(unary_methods) + "]";
+			unary_methods++;
+		} else {
+			vars["MethodDesc"] = vars["ServiceDesc"] + ".Streams[" + as_string(streaming_methods) + "]";
+			streaming_methods++;
+		}
+		GenerateClientMethod(method.get(), printer, vars);
+	}
+
+	//Server Interface
+	printer->Print(vars, "// Server API for $Service$ service\n");
+	printer->Print(vars, "type $Service$Server interface {\n");
+	printer->Indent();
+	for (int i = 0; i < service->method_count(); i++) {
+		GenerateServerMethodSignature(service->method(i).get(), printer, vars);
+		printer->Print("\n");
+	}
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	// Server registration.
+	printer->Print(vars, "func Register$Service$Server(s *$grpc$.Server, srv $Service$Server) {\n");
+	printer->Indent();
+	printer->Print(vars, "s.RegisterService(&$ServiceDesc$, srv)\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+	for (int i = 0; i < service->method_count(); i++) {
+		GenerateServerMethod(service->method(i).get(), printer, vars);
+		printer->Print("\n");
+	}
+
+
+	//Service Descriptor
+	printer->Print(vars, "var $ServiceDesc$ = $grpc$.ServiceDesc{\n");
+	printer->Indent();
+	printer->Print(vars, "ServiceName: \"$Package$.$Service$\",\n");
+	printer->Print(vars, "HandlerType: (*$Service$Server)(nil),\n");
+	printer->Print(vars, "Methods: []$grpc$.MethodDesc{\n");
+	printer->Indent();
+	for (int i = 0; i < service->method_count(); i++) {
+		auto method = service->method(i);
+		vars["Method"] = method->name();
+		vars["Handler"] = "_" + vars["Service"] + "_" + vars["Method"] + "_Handler";
+		if (method->NoStreaming()) {
+			printer->Print("{\n");
+			printer->Indent();
+			printer->Print(vars, "MethodName: \"$Method$\",\n");
+			printer->Print(vars, "Handler: $Handler$, \n");
+			printer->Outdent();
+			printer->Print("},\n");
+		}
+	}
+	printer->Outdent();
+	printer->Print("},\n");
+	printer->Print(vars, "Streams: []$grpc$.StreamDesc{\n");
+	printer->Indent();
+	for (int i = 0; i < service->method_count(); i++) {
+		auto method = service->method(i);
+		vars["Method"] = method->name();
+		vars["Handler"] = "_" + vars["Service"] + "_" + vars["Method"] + "_Handler";
+		if (!method->NoStreaming()) {
+			printer->Print("{\n");
+			printer->Indent();
+			printer->Print(vars, "StreamName: \"$Method$\",\n");
+			printer->Print(vars, "Handler: $Handler$, \n");
+			if (method->ClientOnlyStreaming()) {
+				printer->Print("ClientStreams: true,\n");
+			} else if (method->ServerOnlyStreaming()) {
+				printer->Print("ServerStreams: true,\n");
+			} else {
+				printer->Print("ServerStreams: true,\n");
+				printer->Print("ClientStreams: true,\n");
+			}
+			printer->Outdent();
+			printer->Print("},\n");
+		}
+	}
+	printer->Outdent();
+	printer->Print("},\n");
+	printer->Outdent();
+	printer->Print("}\n\n");
+
+}
+
+
+// Returns source for the service
+grpc::string GenerateServiceSource(grpc_generator::File *file,
+                                   const grpc_generator::Service *service,
+                                   grpc_go_generator::Parameters *parameters) {
+	grpc::string out;
+	auto p = file->CreatePrinter(&out);
+	auto printer = p.get();
+	std::map<grpc::string, grpc::string> vars;
+	vars["Package"] = parameters->package_name;
+	vars["grpc"] = "grpc";
+	vars["context"] = "context";
+	GenerateImports(file, printer, vars);
+	if (parameters->custom_method_io_type != "") {
+		vars["CustomMethodIO"] = parameters->custom_method_io_type;
+	}
+	GenerateService(service, printer, vars);
+	return out;
+}
+}// Namespace grpc_go_generator
\ No newline at end of file
diff --git a/grpc/src/compiler/go_generator.h b/grpc/src/compiler/go_generator.h
new file mode 100644
index 0000000..a8f7a3d
--- /dev/null
+++ b/grpc/src/compiler/go_generator.h
@@ -0,0 +1,61 @@
+/*
+ *
+ * Copyright 2015, Google Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+
+#ifndef GRPC_INTERNAL_COMPILER_GO_GENERATOR_H
+#define GRPC_INTERNAL_COMPILER_GO_GENERATOR_H
+
+//go generator is used to generate GRPC code for serialization system, such as flatbuffers
+#include <memory>
+#include <vector>
+
+#include "src/compiler/schema_interface.h"
+
+namespace grpc_go_generator {
+
+struct Parameters {
+	//Defines the custom parameter types for methods
+	//eg: flatbuffers uses flatbuffers.Builder as input for the client and output for the server
+	grpc::string custom_method_io_type;
+
+	//Package name for the service
+	grpc::string package_name;
+};
+
+// Return the source of the generated service file.
+grpc::string GenerateServiceSource(grpc_generator::File *file,
+                                   const grpc_generator::Service *service,
+                                   grpc_go_generator::Parameters *parameters);
+
+}
+
+#endif  // GRPC_INTERNAL_COMPILER_GO_GENERATOR_H
diff --git a/grpc/src/compiler/schema_interface.h b/grpc/src/compiler/schema_interface.h
new file mode 100644
index 0000000..c9b7f46
--- /dev/null
+++ b/grpc/src/compiler/schema_interface.h
@@ -0,0 +1,112 @@
+/*
+ *
+ * Copyright 2015, Google Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+
+#ifndef GRPC_INTERNAL_COMPILER_SCHEMA_INTERFACE_H
+#define GRPC_INTERNAL_COMPILER_SCHEMA_INTERFACE_H
+
+#include <map>
+#include <memory>
+#include <vector>
+
+ #ifndef GRPC_CUSTOM_STRING
+ #include <string>
+ #define GRPC_CUSTOM_STRING std::string
+ #endif
+
+namespace grpc {
+
+  typedef GRPC_CUSTOM_STRING string;
+
+}  // namespace grpc
+
+namespace grpc_generator {
+
+  // An abstract interface representing a method.
+  struct Method {
+    virtual ~Method() {}
+
+    virtual grpc::string name() const = 0;
+
+    virtual grpc::string input_type_name() const = 0;
+    virtual grpc::string output_type_name() const = 0;
+    virtual grpc::string input_name() const = 0;
+    virtual grpc::string output_name() const = 0;
+
+    virtual bool NoStreaming() const = 0;
+    virtual bool ClientOnlyStreaming() const = 0;
+    virtual bool ServerOnlyStreaming() const = 0;
+    virtual bool BidiStreaming() const = 0;
+  };
+
+  // An abstract interface representing a service.
+  struct Service {
+    virtual ~Service() {}
+
+    virtual grpc::string name() const = 0;
+
+    virtual int method_count() const = 0;
+    virtual std::unique_ptr<const Method> method(int i) const = 0;
+  };
+
+  struct Printer {
+    virtual ~Printer() {}
+
+    virtual void Print(const std::map<grpc::string, grpc::string> &vars,
+                       const char *template_string) = 0;
+    virtual void Print(const char *string) = 0;
+    virtual void Indent() = 0;
+    virtual void Outdent() = 0;
+  };
+
+  // An interface that allows the source generated to be output using various
+  // libraries/idls/serializers.
+  struct File {
+    virtual ~File() {}
+
+    virtual grpc::string filename() const = 0;
+    virtual grpc::string filename_without_ext() const = 0;
+    virtual grpc::string message_header_ext() const = 0;
+    virtual grpc::string service_header_ext() const = 0;
+    virtual grpc::string package() const = 0;
+    virtual std::vector<grpc::string> package_parts() const = 0;
+    virtual grpc::string additional_headers() const = 0;
+    virtual grpc::string additional_imports() const = 0;
+
+    virtual int service_count() const = 0;
+    virtual std::unique_ptr<const Service> service(int i) const = 0;
+
+    virtual std::unique_ptr<Printer> CreatePrinter(grpc::string *str) const = 0;
+  };
+} // namespace grpc_generator
+
+#endif  // GRPC_INTERNAL_COMPILER_SCHEMA_INTERFACE_H
diff --git a/grpc/tests/go_test.go b/grpc/tests/go_test.go
new file mode 100644
index 0000000..f133692
--- /dev/null
+++ b/grpc/tests/go_test.go
@@ -0,0 +1,94 @@
+package testing
+
+import (
+	"../../tests/MyGame/Example"
+
+	"net"
+	"testing"
+
+	"github.com/google/flatbuffers/go"
+	"golang.org/x/net/context"
+	"google.golang.org/grpc"
+)
+
+type server struct{}
+
+// test used to send and receive in grpc methods
+var test string = "Flatbuffers"
+var addr string = "0.0.0.0:50051"
+
+// gRPC server store method
+func (s *server) Store(context context.Context, in *Example.Monster) (*flatbuffers.Builder, error) {
+	b := flatbuffers.NewBuilder(0)
+	i := b.CreateString(test)
+	Example.StatStart(b)
+	Example.StatAddId(b, i)
+	b.Finish(Example.StatEnd(b))
+	return b, nil
+
+}
+
+// gRPC server retrieve method
+func (s *server) Retrieve(context context.Context, in *Example.Stat) (*flatbuffers.Builder, error) {
+	b := flatbuffers.NewBuilder(0)
+	i := b.CreateString(test)
+	Example.MonsterStart(b)
+	Example.MonsterAddName(b, i)
+	b.Finish(Example.MonsterEnd(b))
+	return b, nil
+}
+
+func StoreClient(c Example.MonsterStorageClient, t *testing.T) {
+	b := flatbuffers.NewBuilder(0)
+	i := b.CreateString(test)
+	Example.MonsterStart(b)
+	Example.MonsterAddName(b, i)
+	b.Finish(Example.MonsterEnd(b))
+	out, err := c.Store(context.Background(), b)
+	if err != nil {
+		t.Fatal("Store client failed: %v", err)
+	}
+	if string(out.Id()) != test {
+		t.Errorf("StoreClient failed: expected=%s, got=%s\n", test, out.Id())
+		t.Fail()
+	}
+}
+
+func RetrieveClient(c Example.MonsterStorageClient, t *testing.T) {
+	b := flatbuffers.NewBuilder(0)
+	i := b.CreateString(test)
+	Example.StatStart(b)
+	Example.StatAddId(b, i)
+	b.Finish(Example.StatEnd(b))
+	out, err := c.Retrieve(context.Background(), b)
+	if err != nil {
+		t.Fatal("Retrieve client failed: %v", err)
+	}
+	if string(out.Name()) != test {
+		t.Errorf("RetrieveClient failed: expected=%s, got=%s\n", test, out.Name())
+		t.Fail()
+	}
+}
+
+func TestGRPC(t *testing.T) {
+	lis, err := net.Listen("tcp", addr)
+	if err != nil {
+		t.Fatalf("Failed to listen: %v", err)
+	}
+	ser := grpc.NewServer(grpc.CustomCodec(flatbuffers.FlatbuffersCodec{}))
+	Example.RegisterMonsterStorageServer(ser, &server{})
+	go func() {
+		if err := ser.Serve(lis); err != nil {
+			t.Fatalf("Failed to serve: %v", err)
+			t.FailNow()
+		}
+	}()
+	conn, err := grpc.Dial(addr, grpc.WithInsecure(), grpc.WithCodec(flatbuffers.FlatbuffersCodec{}))
+	if err != nil {
+		t.Fatal("Failed to connect: %v", err)
+	}
+	defer conn.Close()
+	client := Example.NewMonsterStorageClient(conn)
+	StoreClient(client, t)
+	RetrieveClient(client, t)
+}
diff --git a/include/flatbuffers/flatbuffers.h b/include/flatbuffers/flatbuffers.h
index 01ab6db..e830c44 100644
--- a/include/flatbuffers/flatbuffers.h
+++ b/include/flatbuffers/flatbuffers.h
@@ -24,13 +24,20 @@
 #include <cstdlib>
 #include <cstring>
 #include <string>
+#include <utility>
 #include <type_traits>
 #include <vector>
 #include <set>
 #include <algorithm>
-#include <functional>
 #include <memory>
 
+#ifdef _STLPORT_VERSION
+  #define FLATBUFFERS_CPP98_STL
+#endif
+#ifndef FLATBUFFERS_CPP98_STL
+  #include <functional>
+#endif
+
 /// @cond FLATBUFFERS_INTERNAL
 #if __cplusplus <= 199711L && \
     (!defined(_MSC_VER) || _MSC_VER < 1600) && \
@@ -123,9 +130,14 @@
 // In 32bits, this evaluates to 2GB - 1
 #define FLATBUFFERS_MAX_BUFFER_SIZE ((1ULL << (sizeof(soffset_t) * 8 - 1)) - 1)
 
+// We support aligning the contents of buffers up to this size.
+#define FLATBUFFERS_MAX_ALIGNMENT 16
+
+#ifndef FLATBUFFERS_CPP98_STL
 // Pointer to relinquished memory.
 typedef std::unique_ptr<uint8_t, std::function<void(uint8_t * /* unused */)>>
           unique_ptr_t;
+#endif
 
 // Wrapper for uoffset_t to allow safe template specialization.
 template<typename T> struct Offset {
@@ -142,39 +154,43 @@
   (void)endiantest;
 }
 
+template<typename T> T EndianSwap(T t) {
+  #if defined(_MSC_VER)
+    #define FLATBUFFERS_BYTESWAP16 _byteswap_ushort
+    #define FLATBUFFERS_BYTESWAP32 _byteswap_ulong
+    #define FLATBUFFERS_BYTESWAP64 _byteswap_uint64
+  #else
+    #if defined(__GNUC__) && __GNUC__ * 100 + __GNUC_MINOR__ < 408
+      // __builtin_bswap16 was missing prior to GCC 4.8.
+      #define FLATBUFFERS_BYTESWAP16(x) \
+        static_cast<uint16_t>(__builtin_bswap32(static_cast<uint32_t>(x) << 16))
+    #else
+      #define FLATBUFFERS_BYTESWAP16 __builtin_bswap16
+    #endif
+    #define FLATBUFFERS_BYTESWAP32 __builtin_bswap32
+    #define FLATBUFFERS_BYTESWAP64 __builtin_bswap64
+  #endif
+  if (sizeof(T) == 1) {   // Compile-time if-then's.
+    return t;
+  } else if (sizeof(T) == 2) {
+    auto r = FLATBUFFERS_BYTESWAP16(*reinterpret_cast<uint16_t *>(&t));
+    return *reinterpret_cast<T *>(&r);
+  } else if (sizeof(T) == 4) {
+    auto r = FLATBUFFERS_BYTESWAP32(*reinterpret_cast<uint32_t *>(&t));
+    return *reinterpret_cast<T *>(&r);
+  } else if (sizeof(T) == 8) {
+    auto r = FLATBUFFERS_BYTESWAP64(*reinterpret_cast<uint64_t *>(&t));
+    return *reinterpret_cast<T *>(&r);
+  } else {
+    assert(0);
+  }
+}
+
 template<typename T> T EndianScalar(T t) {
   #if FLATBUFFERS_LITTLEENDIAN
     return t;
   #else
-    #if defined(_MSC_VER)
-      #pragma push_macro("__builtin_bswap16")
-      #pragma push_macro("__builtin_bswap32")
-      #pragma push_macro("__builtin_bswap64")
-      #define __builtin_bswap16 _byteswap_ushort
-      #define __builtin_bswap32 _byteswap_ulong
-      #define __builtin_bswap64 _byteswap_uint64
-    #endif
-    // If you're on the few remaining big endian platforms, we make the bold
-    // assumption you're also on gcc/clang, and thus have bswap intrinsics:
-    if (sizeof(T) == 1) {   // Compile-time if-then's.
-      return t;
-    } else if (sizeof(T) == 2) {
-      auto r = __builtin_bswap16(*reinterpret_cast<uint16_t *>(&t));
-      return *reinterpret_cast<T *>(&r);
-    } else if (sizeof(T) == 4) {
-      auto r = __builtin_bswap32(*reinterpret_cast<uint32_t *>(&t));
-      return *reinterpret_cast<T *>(&r);
-    } else if (sizeof(T) == 8) {
-      auto r = __builtin_bswap64(*reinterpret_cast<uint64_t *>(&t));
-      return *reinterpret_cast<T *>(&r);
-    } else {
-      assert(0);
-    }
-    #if defined(_MSC_VER)
-      #pragma pop_macro("__builtin_bswap16")
-      #pragma pop_macro("__builtin_bswap32")
-      #pragma pop_macro("__builtin_bswap64")
-    #endif
+    return EndianSwap(t);
   #endif
 }
 
@@ -234,23 +250,19 @@
 
 // An STL compatible iterator implementation for Vector below, effectively
 // calling Get() for every element.
-template<typename T, bool bConst>
-struct VectorIterator : public
-  std::iterator < std::input_iterator_tag,
-  typename std::conditional < bConst,
-  const typename IndirectHelper<T>::return_type,
-  typename IndirectHelper<T>::return_type > ::type, uoffset_t > {
+template<typename T, typename IT>
+struct VectorIterator
+    : public std::iterator<std::input_iterator_tag, IT, uoffset_t> {
 
-  typedef std::iterator<std::input_iterator_tag,
-    typename std::conditional<bConst,
-    const typename IndirectHelper<T>::return_type,
-    typename IndirectHelper<T>::return_type>::type, uoffset_t> super_type;
+  typedef std::iterator<std::input_iterator_tag, IT, uoffset_t> super_type;
 
 public:
   VectorIterator(const uint8_t *data, uoffset_t i) :
-      data_(data + IndirectHelper<T>::element_stride * i) {};
+      data_(data + IndirectHelper<T>::element_stride * i) {}
   VectorIterator(const VectorIterator &other) : data_(other.data_) {}
+  #ifndef FLATBUFFERS_CPP98_STL
   VectorIterator(VectorIterator &&other) : data_(std::move(other.data_)) {}
+  #endif
 
   VectorIterator &operator=(const VectorIterator &other) {
     data_ = other.data_;
@@ -301,8 +313,10 @@
 // Vector::data() assumes the vector elements start after the length field.
 template<typename T> class Vector {
 public:
-  typedef VectorIterator<T, false> iterator;
-  typedef VectorIterator<T, true> const_iterator;
+  typedef VectorIterator<T, typename IndirectHelper<T>::mutable_return_type>
+    iterator;
+  typedef VectorIterator<T, typename IndirectHelper<T>::return_type>
+    const_iterator;
 
   uoffset_t size() const { return EndianScalar(length_); }
 
@@ -349,7 +363,8 @@
   void MutateOffset(uoffset_t i, const uint8_t *val) {
     assert(i < size());
     assert(sizeof(T) == sizeof(uoffset_t));
-    WriteScalar(data() + i, val - (Data() + i * sizeof(uoffset_t)));
+    WriteScalar(data() + i,
+                static_cast<uoffset_t>(val - (Data() + i * sizeof(uoffset_t))));
   }
 
   // Get a mutable pointer to tables/strings inside this vector.
@@ -471,6 +486,7 @@
     cur_ = buf_ + reserved_;
   }
 
+  #ifndef FLATBUFFERS_CPP98_STL
   // Relinquish the pointer to the caller.
   unique_ptr_t release() {
     // Actually deallocate from the start of the allocated memory.
@@ -486,6 +502,7 @@
 
     return retval;
   }
+  #endif
 
   size_t growth_policy(size_t bytes) {
     return (bytes / 2) & ~(sizeof(largest_scalar_t) - 1);
@@ -562,6 +579,14 @@
 inline size_t PaddingBytes(size_t buf_size, size_t scalar_size) {
   return ((~buf_size) + 1) & (scalar_size - 1);
 }
+
+template <typename T> const T* data(const std::vector<T> &v) {
+  return v.empty() ? nullptr : &v.front();
+}
+template <typename T> T* data(std::vector<T> &v) {
+  return v.empty() ? nullptr : &v.front();
+}
+
 /// @endcond
 
 /// @addtogroup flatbuffers_cpp_api
@@ -627,6 +652,7 @@
   /// @return Returns a `uint8_t` pointer to the unfinished buffer.
   uint8_t *GetCurrentBufferPointer() const { return buf_.data(); }
 
+  #ifndef FLATBUFFERS_CPP98_STL
   /// @brief Get the released pointer to the serialized buffer.
   /// @warning Do NOT attempt to use this FlatBufferBuilder afterwards!
   /// @return The `unique_ptr` returned has a special allocator that knows how
@@ -637,6 +663,17 @@
     Finished();
     return buf_.release();
   }
+  #endif
+
+  /// @brief get the minimum alignment this buffer needs to be accessed
+  /// properly. This is only known once all elements have been written (after
+  /// you call Finish()). You can use this information if you need to embed
+  /// a FlatBuffer in some other buffer, such that you can later read it
+  /// without first having to copy it into its own buffer.
+  size_t GetBufferMinAlignment() {
+    Finished();
+    return minalign_;
+  }
 
   /// @cond FLATBUFFERS_INTERNAL
   void Finished() const {
@@ -674,11 +711,13 @@
   void PopBytes(size_t amount) { buf_.pop(amount); }
 
   template<typename T> void AssertScalarT() {
+    #ifndef FLATBUFFERS_CPP98_STL
     // The code assumes power of 2 sizes and endian-swap-ability.
     static_assert(std::is_scalar<T>::value
         // The Offset<T> type is essentially a scalar but fails is_scalar.
         || sizeof(T) == sizeof(Offset<void>),
            "T must be a scalar type");
+    #endif
   }
 
   // Write a single aligned scalar to the buffer
@@ -981,9 +1020,21 @@
   /// @return Returns a typed `Offset` into the serialized data indicating
   /// where the vector is stored.
   template<typename T> Offset<Vector<T>> CreateVector(const std::vector<T> &v) {
-    return CreateVector(v.data(), v.size());
+    return CreateVector(data(v), v.size());
   }
 
+  // vector<bool> may be implemented using a bit-set, so we can't access it as
+  // an array. Instead, read elements manually.
+  // Background: https://isocpp.org/blog/2012/11/on-vectorbool
+  Offset<Vector<uint8_t>> CreateVector(const std::vector<bool> &v) {
+    StartVector(v.size(), sizeof(uint8_t));
+    for (auto i = v.size(); i > 0; ) {
+      PushElement(static_cast<uint8_t>(v[--i]));
+    }
+    return Offset<Vector<uint8_t>>(EndVector(v.size()));
+  }
+
+  #ifndef FLATBUFFERS_CPP98_STL
   /// @brief Serialize values returned by a function into a FlatBuffer `vector`.
   /// This is a convenience function that takes care of iteration for you.
   /// @tparam T The data type of the `std::vector` elements.
@@ -995,8 +1046,9 @@
       const std::function<T (size_t i)> &f) {
     std::vector<T> elems(vector_size);
     for (size_t i = 0; i < vector_size; i++) elems[i] = f(i);
-    return CreateVector(elems.data(), elems.size());
+    return CreateVector(elems);
   }
+  #endif
 
   /// @brief Serialize a `std::vector<std::string>` into a FlatBuffer `vector`.
   /// This is a convenience function for a common case.
@@ -1008,7 +1060,7 @@
       const std::vector<std::string> &v) {
     std::vector<Offset<String>> offsets(v.size());
     for (size_t i = 0; i < v.size(); i++) offsets[i] = CreateString(v[i]);
-    return CreateVector(offsets.data(), offsets.size());
+    return CreateVector(offsets);
   }
 
   /// @brief Serialize an array of structs into a FlatBuffer `vector`.
@@ -1033,7 +1085,7 @@
   /// where the vector is stored.
   template<typename T> Offset<Vector<const T *>> CreateVectorOfStructs(
       const std::vector<T> &v) {
-    return CreateVectorOfStructs(v.data(), v.size());
+    return CreateVectorOfStructs(data(v), v.size());
   }
 
   /// @cond FLATBUFFERS_INTERNAL
@@ -1075,7 +1127,7 @@
   /// where the vector is stored.
   template<typename T> Offset<Vector<Offset<T>>> CreateVectorOfSortedTables(
       std::vector<Offset<T>> *v) {
-    return CreateVectorOfSortedTables(v->data(), v->size());
+    return CreateVectorOfSortedTables(data(*v), v->size());
   }
 
   /// @brief Specialized version of `CreateVector` for non-copying use cases.
@@ -1118,17 +1170,20 @@
   /// will be prefixed with a standard FlatBuffers file header.
   template<typename T> void Finish(Offset<T> root,
                                    const char *file_identifier = nullptr) {
-    NotNested();
-    // This will cause the whole buffer to be aligned.
-    PreAlign(sizeof(uoffset_t) + (file_identifier ? kFileIdentifierLength : 0),
-             minalign_);
-    if (file_identifier) {
-      assert(strlen(file_identifier) == kFileIdentifierLength);
-      buf_.push(reinterpret_cast<const uint8_t *>(file_identifier),
-                kFileIdentifierLength);
-    }
-    PushElement(ReferTo(root.o));  // Location of root.
-    finished = true;
+
+    Finish(root.o, file_identifier, false);
+  }
+
+  /// @brief Finish a buffer with a 32 bit size field pre-fixed (size of the
+  /// buffer following the size field). These buffers are NOT compatible
+  /// with standard buffers created by Finish, i.e. you can't call GetRoot
+  /// on them, you have to use GetSizePrefixedRoot instead.
+  /// All >32 bit quantities in this buffer will be aligned when the whole
+  /// size pre-fixed buffer is aligned.
+  /// These kinds of buffers are useful for creating a stream of FlatBuffers.
+  template<typename T> void FinishSizePrefixed(Offset<T> root,
+                                   const char *file_identifier = nullptr) {
+    Finish(root.o, file_identifier, true);
   }
 
  private:
@@ -1136,6 +1191,25 @@
   FlatBufferBuilder(const FlatBufferBuilder &);
   FlatBufferBuilder &operator=(const FlatBufferBuilder &);
 
+  void Finish(uoffset_t root, const char *file_identifier, bool size_prefix) {
+    NotNested();
+    // This will cause the whole buffer to be aligned.
+    PreAlign((size_prefix ? sizeof(uoffset_t) : 0) +
+             sizeof(uoffset_t) +
+             (file_identifier ? kFileIdentifierLength : 0),
+             minalign_);
+    if (file_identifier) {
+      assert(strlen(file_identifier) == kFileIdentifierLength);
+      buf_.push(reinterpret_cast<const uint8_t *>(file_identifier),
+                kFileIdentifierLength);
+    }
+    PushElement(ReferTo(root));  // Location of root.
+    if (size_prefix) {
+      PushElement(GetSize());
+    }
+    finished = true;
+  }
+
   struct FieldLoc {
     uoffset_t off;
     voffset_t id;
@@ -1189,7 +1263,11 @@
   return GetMutableRoot<T>(const_cast<void *>(buf));
 }
 
-/// Helpers to get a typed pointer to objects that are currently beeing built.
+template<typename T> const T *GetSizePrefixedRoot(const void *buf) {
+  return GetRoot<T>(reinterpret_cast<const uint8_t *>(buf) + sizeof(uoffset_t));
+}
+
+/// Helpers to get a typed pointer to objects that are currently being built.
 /// @warning Creating new objects will lead to reallocations and invalidates
 /// the pointer!
 template<typename T> T *GetMutableTemporaryPointer(FlatBufferBuilder &fbb,
@@ -1313,16 +1391,17 @@
     return true;
   }
 
-  // Verify this whole buffer, starting with root type T.
-  template<typename T> bool VerifyBuffer(const char *identifier) {
-    if (identifier && (size_t(end_ - buf_) < 2 * sizeof(flatbuffers::uoffset_t) ||
-                       !BufferHasIdentifier(buf_, identifier))) {
+  template<typename T> bool VerifyBufferFromStart(const char *identifier,
+                                                  const uint8_t *start) {
+    if (identifier &&
+        (size_t(end_ - start) < 2 * sizeof(flatbuffers::uoffset_t) ||
+         !BufferHasIdentifier(start, identifier))) {
       return false;
     }
 
     // Call T::Verify, which must be in the generated code for this type.
-    return Verify<uoffset_t>(buf_) &&
-      reinterpret_cast<const T *>(buf_ + ReadScalar<uoffset_t>(buf_))->
+    return Verify<uoffset_t>(start) &&
+      reinterpret_cast<const T *>(start + ReadScalar<uoffset_t>(start))->
         Verify(*this)
         #ifdef FLATBUFFERS_TRACK_VERIFIER_BUFFER_SIZE
           && GetComputedSize()
@@ -1330,6 +1409,17 @@
             ;
   }
 
+  // Verify this whole buffer, starting with root type T.
+  template<typename T> bool VerifyBuffer(const char *identifier) {
+    return VerifyBufferFromStart<T>(identifier, buf_);
+  }
+
+  template<typename T> bool VerifySizePrefixedBuffer(const char *identifier) {
+    return Verify<uoffset_t>(buf_) &&
+           ReadScalar<uoffset_t>(buf_) == end_ - buf_ - sizeof(uoffset_t) &&
+           VerifyBufferFromStart<T>(identifier, buf_ + sizeof(uoffset_t));
+  }
+
   // Called at the start of a table to increase counters measuring data
   // structure depth and amount, and possibly bails out with false if
   // limits set by the constructor have been hit. Needs to be balanced
@@ -1351,7 +1441,7 @@
   size_t GetComputedSize() const {
     uintptr_t size = upper_bound_ - buf_;
     // Align the size to uoffset_t
-    size = (size - 1 + sizeof(uoffset_t)) & -uintptr_t(sizeof(uoffset_t));
+    size = (size - 1 + sizeof(uoffset_t)) & ~(sizeof(uoffset_t) - 1);
     return (buf_  + size > end_) ?  0 : size;
   }
   #endif
@@ -1401,11 +1491,6 @@
     return ReadScalar<T>(&data_[o]);
   }
 
-  template<typename T> T GetPointer(uoffset_t o) const {
-    auto p = &data_[o];
-    return reinterpret_cast<T>(p + ReadScalar<uoffset_t>(p));
-  }
-
   template<typename T> T GetStruct(uoffset_t o) const {
     return reinterpret_cast<T>(&data_[o]);
   }
@@ -1421,11 +1506,15 @@
 // omitted and added at will, but uses an extra indirection to read.
 class Table {
  public:
+  const uint8_t *GetVTable() const {
+    return data_ - ReadScalar<soffset_t>(data_);
+  }
+
   // This gets the field offset for any of the functions below it, or 0
   // if the field was not present.
   voffset_t GetOptionalFieldOffset(voffset_t field) const {
     // The vtable offset is always at the start.
-    auto vtable = data_ - ReadScalar<soffset_t>(data_);
+    auto vtable = GetVTable();
     // The first element is the size of the vtable (fields + type id + itself).
     auto vtsize = ReadScalar<voffset_t>(vtable);
     // If the field we're accessing is outside the vtable, we're reading older
@@ -1465,7 +1554,8 @@
   bool SetPointer(voffset_t field, const uint8_t *val) {
     auto field_offset = GetOptionalFieldOffset(field);
     if (!field_offset) return false;
-    WriteScalar(data_ + field_offset, val - (data_ + field_offset));
+    WriteScalar(data_ + field_offset,
+                static_cast<uoffset_t>(val - (data_ + field_offset)));
     return true;
   }
 
@@ -1477,8 +1567,6 @@
     return const_cast<Table *>(this)->GetAddressOf(field);
   }
 
-  uint8_t *GetVTable() { return data_ - ReadScalar<soffset_t>(data_); }
-
   bool CheckField(voffset_t field) const {
     return GetOptionalFieldOffset(field) != 0;
   }
@@ -1488,7 +1576,7 @@
   bool VerifyTableStart(Verifier &verifier) const {
     // Check the vtable offset.
     if (!verifier.Verify<soffset_t>(data_)) return false;
-    auto vtable = data_ - ReadScalar<soffset_t>(data_);
+    auto vtable = GetVTable();
     // Check the vtable size field, then check vtable fits in its entirety.
     return verifier.VerifyComplexity() &&
            verifier.Verify<voffset_t>(vtable) &&
@@ -1523,6 +1611,68 @@
   uint8_t data_[1];
 };
 
+/// @brief This can compute the start of a FlatBuffer from a root pointer, i.e.
+/// it is the opposite transformation of GetRoot().
+/// This may be useful if you want to pass on a root and have the recipient
+/// delete the buffer afterwards.
+inline const uint8_t *GetBufferStartFromRootPointer(const void *root) {
+  auto table = reinterpret_cast<const Table *>(root);
+  auto vtable = table->GetVTable();
+  // Either the vtable is before the root or after the root.
+  auto start = std::min(vtable, reinterpret_cast<const uint8_t *>(root));
+  // Align to at least sizeof(uoffset_t).
+  start = reinterpret_cast<const uint8_t *>(
+            reinterpret_cast<uintptr_t>(start) & ~(sizeof(uoffset_t) - 1));
+  // Additionally, there may be a file_identifier in the buffer, and the root
+  // offset. The buffer may have been aligned to any size between
+  // sizeof(uoffset_t) and FLATBUFFERS_MAX_ALIGNMENT (see "force_align").
+  // Sadly, the exact alignment is only known when constructing the buffer,
+  // since it depends on the presence of values with said alignment properties.
+  // So instead, we simply look at the next uoffset_t values (root,
+  // file_identifier, and alignment padding) to see which points to the root.
+  // None of the other values can "impersonate" the root since they will either
+  // be 0 or four ASCII characters.
+  static_assert(FlatBufferBuilder::kFileIdentifierLength == sizeof(uoffset_t),
+                "file_identifier is assumed to be the same size as uoffset_t");
+  for (auto possible_roots = FLATBUFFERS_MAX_ALIGNMENT / sizeof(uoffset_t) + 1;
+       possible_roots;
+       possible_roots--) {
+      start -= sizeof(uoffset_t);
+      if (ReadScalar<uoffset_t>(start) + start ==
+          reinterpret_cast<const uint8_t *>(root)) return start;
+  }
+  // We didn't find the root, either the "root" passed isn't really a root,
+  // or the buffer is corrupt.
+  // Assert, because calling this function with bad data may cause reads
+  // outside of buffer boundaries.
+  assert(false);
+  return nullptr;
+}
+
+// Base class for native objects (FlatBuffer data de-serialized into native
+// C++ data structures).
+// Contains no functionality, purely documentative.
+struct NativeTable {
+};
+
+/// @brief Function types to be used with resolving hashes into objects and
+/// back again. The resolver gets a pointer to a field inside an object API
+/// object that is of the type specified in the schema using the attribute
+/// `cpp_type` (it is thus important whatever you write to this address
+/// matches that type). The value of this field is initially null, so you
+/// may choose to implement a delayed binding lookup using this function
+/// if you wish. The resolver does the opposite lookup, for when the object
+/// is being serialized again.
+typedef uint64_t hash_value_t;
+#ifdef FLATBUFFERS_CPP98_STL
+  typedef void (*resolver_function_t)(void **pointer_adr, hash_value_t hash);
+  typedef hash_value_t (*rehasher_function_t)(void *pointer);
+#else
+  typedef std::function<void (void **pointer_adr, hash_value_t hash)>
+          resolver_function_t;
+  typedef std::function<hash_value_t (void *pointer)> rehasher_function_t;
+#endif
+
 // Helper function to test if a field is present, using any of the field
 // enums in the generated code.
 // `table` must be a generated table type. Since this is a template parameter,
diff --git a/include/flatbuffers/idl.h b/include/flatbuffers/idl.h
index dddfab2..6ae8dd2 100644
--- a/include/flatbuffers/idl.h
+++ b/include/flatbuffers/idl.h
@@ -234,6 +234,8 @@
                    // written in new data nor accessed in new code.
   bool required;   // Field must always be present.
   bool key;        // Field functions as a key for creating sorted vectors.
+  bool native_inline;  // Field will be defined inline (instead of as a pointer)
+                       // for native tables if field is a struct.
   size_t padding;  // Bytes to always pad after this field.
 };
 
@@ -311,6 +313,14 @@
   Type underlying_type;
 };
 
+inline bool EqualByName(const Type &a, const Type &b) {
+  return a.base_type == b.base_type && a.element == b.element &&
+         (a.struct_def == b.struct_def ||
+          a.struct_def->name == b.struct_def->name) &&
+         (a.enum_def == b.enum_def ||
+          a.enum_def->name == b.enum_def->name);
+}
+
 struct RPCCall {
   std::string name;
   SymbolTable<Value> attributes;
@@ -338,7 +348,11 @@
   bool skip_unexpected_fields_in_json;
   bool generate_name_strings;
   bool escape_proto_identifiers;
-  
+  bool generate_object_based_api;
+  std::string cpp_object_api_pointer_type;
+  bool union_value_namespacing;
+  bool allow_non_utf8;
+
   // Possible options for the more general generator below.
   enum Language { kJava, kCSharp, kGo, kMAX };
 
@@ -358,6 +372,10 @@
       skip_unexpected_fields_in_json(false),
       generate_name_strings(false),
       escape_proto_identifiers(false),
+      generate_object_based_api(false),
+      cpp_object_api_pointer_type("std::unique_ptr"),
+      union_value_namespacing(true),
+      allow_non_utf8(false),
       lang(IDLOptions::kJava) {}
 };
 
@@ -436,6 +454,9 @@
     known_attributes_["csharp_partial"] = true;
     known_attributes_["streaming"] = true;
     known_attributes_["idempotent"] = true;
+    known_attributes_["cpp_type"] = true;
+    known_attributes_["cpp_ptr_type"] = true;
+    known_attributes_["native_inline"] = true;
   }
 
   ~Parser() {
@@ -471,6 +492,10 @@
   // See reflection/reflection.fbs
   void Serialize();
 
+  // Checks that the schema represented by this parser is a safe evolution
+  // of the schema provided. Returns non-empty error on any problems.
+  std::string ConformTo(const Parser &base);
+
   FLATBUFFERS_CHECKED_ERROR CheckBitsFit(int64_t val, size_t bits);
 
 private:
@@ -578,7 +603,9 @@
 // if it is less than 0, no linefeeds will be generated either.
 // See idl_gen_text.cpp.
 // strict_json adds "quotes" around field names if true.
-extern void GenerateText(const Parser &parser,
+// If the flatbuffer cannot be encoded in JSON (e.g., it contains non-UTF-8
+// byte arrays in String values), returns false.
+extern bool GenerateText(const Parser &parser,
                          const void *flatbuffer,
                          std::string *text);
 extern bool GenerateTextFile(const Parser &parser,
@@ -622,8 +649,8 @@
 // Generate Php code from the definitions in the Parser object.
 // See idl_gen_php.
 extern bool GeneratePhp(const Parser &parser,
-       const std::string &path,
-       const std::string &file_name);
+                        const std::string &path,
+                        const std::string &file_name);
 
 // Generate Python files from the definitions in the Parser object.
 // See idl_gen_python.cpp.
@@ -681,11 +708,17 @@
                                   const std::string &path,
                                   const std::string &file_name);
 
-// Generate GRPC interfaces.
+// Generate GRPC Cpp interfaces.
 // See idl_gen_grpc.cpp.
-bool GenerateGRPC(const Parser &parser,
-                  const std::string &path,
-                  const std::string &file_name);
+bool GenerateCppGRPC(const Parser &parser,
+                     const std::string &path,
+                     const std::string &file_name);
+
+// Generate GRPC Go interfaces.
+// See idl_gen_grpc.cpp.
+bool GenerateGoGRPC(const Parser &parser,
+                    const std::string &path,
+                    const std::string &file_name);
 
 }  // namespace flatbuffers
 
diff --git a/include/flatbuffers/reflection.h b/include/flatbuffers/reflection.h
index 8709143..ae331ce 100644
--- a/include/flatbuffers/reflection.h
+++ b/include/flatbuffers/reflection.h
@@ -370,6 +370,7 @@
                          uoffset_t elem_size, std::vector<uint8_t> *flatbuf,
                          const reflection::Object *root_table = nullptr);
 
+#ifndef FLATBUFFERS_CPP98_STL
 template <typename T>
 void ResizeVector(const reflection::Schema &schema, uoffset_t newsize, T val,
                   const Vector<T> *vec, std::vector<uint8_t> *flatbuf,
@@ -391,6 +392,7 @@
     }
   }
 }
+#endif
 
 // Adds any new data (in the form of a new FlatBuffer) to an existing
 // FlatBuffer. This can be used when any of the above methods are not
diff --git a/include/flatbuffers/reflection_generated.h b/include/flatbuffers/reflection_generated.h
index eb98185..b6233ff 100644
--- a/include/flatbuffers/reflection_generated.h
+++ b/include/flatbuffers/reflection_generated.h
@@ -38,9 +38,7 @@
   String = 13,
   Vector = 14,
   Obj = 15,
-  Union = 16,
-  MIN = None,
-  MAX = Union
+  Union = 16
 };
 
 inline const char **EnumNamesBaseType() {
@@ -83,9 +81,9 @@
 };
 
 inline flatbuffers::Offset<Type> CreateType(flatbuffers::FlatBufferBuilder &_fbb,
-   BaseType base_type = None,
-   BaseType element = None,
-   int32_t index = -1) {
+    BaseType base_type = None,
+    BaseType element = None,
+    int32_t index = -1) {
   TypeBuilder builder_(_fbb);
   builder_.add_index(index);
   builder_.add_element(element);
@@ -127,14 +125,20 @@
 };
 
 inline flatbuffers::Offset<KeyValue> CreateKeyValue(flatbuffers::FlatBufferBuilder &_fbb,
-   flatbuffers::Offset<flatbuffers::String> key = 0,
-   flatbuffers::Offset<flatbuffers::String> value = 0) {
+    flatbuffers::Offset<flatbuffers::String> key = 0,
+    flatbuffers::Offset<flatbuffers::String> value = 0) {
   KeyValueBuilder builder_(_fbb);
   builder_.add_value(value);
   builder_.add_key(key);
   return builder_.Finish();
 }
 
+inline flatbuffers::Offset<KeyValue> CreateKeyValueDirect(flatbuffers::FlatBufferBuilder &_fbb,
+    const char *key = nullptr,
+    const char *value = nullptr) {
+  return CreateKeyValue(_fbb, key ? _fbb.CreateString(key) : 0, value ? _fbb.CreateString(value) : 0);
+}
+
 struct EnumVal FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
   enum {
     VT_NAME = 4,
@@ -173,9 +177,9 @@
 };
 
 inline flatbuffers::Offset<EnumVal> CreateEnumVal(flatbuffers::FlatBufferBuilder &_fbb,
-   flatbuffers::Offset<flatbuffers::String> name = 0,
-   int64_t value = 0,
-   flatbuffers::Offset<Object> object = 0) {
+    flatbuffers::Offset<flatbuffers::String> name = 0,
+    int64_t value = 0,
+    flatbuffers::Offset<Object> object = 0) {
   EnumValBuilder builder_(_fbb);
   builder_.add_value(value);
   builder_.add_object(object);
@@ -183,6 +187,13 @@
   return builder_.Finish();
 }
 
+inline flatbuffers::Offset<EnumVal> CreateEnumValDirect(flatbuffers::FlatBufferBuilder &_fbb,
+    const char *name = nullptr,
+    int64_t value = 0,
+    flatbuffers::Offset<Object> object = 0) {
+  return CreateEnumVal(_fbb, name ? _fbb.CreateString(name) : 0, value, object);
+}
+
 struct Enum FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
   enum {
     VT_NAME = 4,
@@ -235,11 +246,11 @@
 };
 
 inline flatbuffers::Offset<Enum> CreateEnum(flatbuffers::FlatBufferBuilder &_fbb,
-   flatbuffers::Offset<flatbuffers::String> name = 0,
-   flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<EnumVal>>> values = 0,
-   bool is_union = false,
-   flatbuffers::Offset<Type> underlying_type = 0,
-   flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<KeyValue>>> attributes = 0) {
+    flatbuffers::Offset<flatbuffers::String> name = 0,
+    flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<EnumVal>>> values = 0,
+    bool is_union = false,
+    flatbuffers::Offset<Type> underlying_type = 0,
+    flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<KeyValue>>> attributes = 0) {
   EnumBuilder builder_(_fbb);
   builder_.add_attributes(attributes);
   builder_.add_underlying_type(underlying_type);
@@ -249,6 +260,15 @@
   return builder_.Finish();
 }
 
+inline flatbuffers::Offset<Enum> CreateEnumDirect(flatbuffers::FlatBufferBuilder &_fbb,
+    const char *name = nullptr,
+    const std::vector<flatbuffers::Offset<EnumVal>> *values = nullptr,
+    bool is_union = false,
+    flatbuffers::Offset<Type> underlying_type = 0,
+    const std::vector<flatbuffers::Offset<KeyValue>> *attributes = nullptr) {
+  return CreateEnum(_fbb, name ? _fbb.CreateString(name) : 0, values ? _fbb.CreateVector<flatbuffers::Offset<EnumVal>>(*values) : 0, is_union, underlying_type, attributes ? _fbb.CreateVector<flatbuffers::Offset<KeyValue>>(*attributes) : 0);
+}
+
 struct Field FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
   enum {
     VT_NAME = 4,
@@ -318,16 +338,16 @@
 };
 
 inline flatbuffers::Offset<Field> CreateField(flatbuffers::FlatBufferBuilder &_fbb,
-   flatbuffers::Offset<flatbuffers::String> name = 0,
-   flatbuffers::Offset<Type> type = 0,
-   uint16_t id = 0,
-   uint16_t offset = 0,
-   int64_t default_integer = 0,
-   double default_real = 0.0,
-   bool deprecated = false,
-   bool required = false,
-   bool key = false,
-   flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<KeyValue>>> attributes = 0) {
+    flatbuffers::Offset<flatbuffers::String> name = 0,
+    flatbuffers::Offset<Type> type = 0,
+    uint16_t id = 0,
+    uint16_t offset = 0,
+    int64_t default_integer = 0,
+    double default_real = 0.0,
+    bool deprecated = false,
+    bool required = false,
+    bool key = false,
+    flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<KeyValue>>> attributes = 0) {
   FieldBuilder builder_(_fbb);
   builder_.add_default_real(default_real);
   builder_.add_default_integer(default_integer);
@@ -342,6 +362,20 @@
   return builder_.Finish();
 }
 
+inline flatbuffers::Offset<Field> CreateFieldDirect(flatbuffers::FlatBufferBuilder &_fbb,
+    const char *name = nullptr,
+    flatbuffers::Offset<Type> type = 0,
+    uint16_t id = 0,
+    uint16_t offset = 0,
+    int64_t default_integer = 0,
+    double default_real = 0.0,
+    bool deprecated = false,
+    bool required = false,
+    bool key = false,
+    const std::vector<flatbuffers::Offset<KeyValue>> *attributes = nullptr) {
+  return CreateField(_fbb, name ? _fbb.CreateString(name) : 0, type, id, offset, default_integer, default_real, deprecated, required, key, attributes ? _fbb.CreateVector<flatbuffers::Offset<KeyValue>>(*attributes) : 0);
+}
+
 struct Object FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
   enum {
     VT_NAME = 4,
@@ -396,12 +430,12 @@
 };
 
 inline flatbuffers::Offset<Object> CreateObject(flatbuffers::FlatBufferBuilder &_fbb,
-   flatbuffers::Offset<flatbuffers::String> name = 0,
-   flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<Field>>> fields = 0,
-   bool is_struct = false,
-   int32_t minalign = 0,
-   int32_t bytesize = 0,
-   flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<KeyValue>>> attributes = 0) {
+    flatbuffers::Offset<flatbuffers::String> name = 0,
+    flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<Field>>> fields = 0,
+    bool is_struct = false,
+    int32_t minalign = 0,
+    int32_t bytesize = 0,
+    flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<KeyValue>>> attributes = 0) {
   ObjectBuilder builder_(_fbb);
   builder_.add_attributes(attributes);
   builder_.add_bytesize(bytesize);
@@ -412,6 +446,16 @@
   return builder_.Finish();
 }
 
+inline flatbuffers::Offset<Object> CreateObjectDirect(flatbuffers::FlatBufferBuilder &_fbb,
+    const char *name = nullptr,
+    const std::vector<flatbuffers::Offset<Field>> *fields = nullptr,
+    bool is_struct = false,
+    int32_t minalign = 0,
+    int32_t bytesize = 0,
+    const std::vector<flatbuffers::Offset<KeyValue>> *attributes = nullptr) {
+  return CreateObject(_fbb, name ? _fbb.CreateString(name) : 0, fields ? _fbb.CreateVector<flatbuffers::Offset<Field>>(*fields) : 0, is_struct, minalign, bytesize, attributes ? _fbb.CreateVector<flatbuffers::Offset<KeyValue>>(*attributes) : 0);
+}
+
 struct Schema FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
   enum {
     VT_OBJECTS = 4,
@@ -462,11 +506,11 @@
 };
 
 inline flatbuffers::Offset<Schema> CreateSchema(flatbuffers::FlatBufferBuilder &_fbb,
-   flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<Object>>> objects = 0,
-   flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<Enum>>> enums = 0,
-   flatbuffers::Offset<flatbuffers::String> file_ident = 0,
-   flatbuffers::Offset<flatbuffers::String> file_ext = 0,
-   flatbuffers::Offset<Object> root_table = 0) {
+    flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<Object>>> objects = 0,
+    flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<Enum>>> enums = 0,
+    flatbuffers::Offset<flatbuffers::String> file_ident = 0,
+    flatbuffers::Offset<flatbuffers::String> file_ext = 0,
+    flatbuffers::Offset<Object> root_table = 0) {
   SchemaBuilder builder_(_fbb);
   builder_.add_root_table(root_table);
   builder_.add_file_ext(file_ext);
@@ -476,17 +520,36 @@
   return builder_.Finish();
 }
 
-inline const reflection::Schema *GetSchema(const void *buf) { return flatbuffers::GetRoot<reflection::Schema>(buf); }
+inline flatbuffers::Offset<Schema> CreateSchemaDirect(flatbuffers::FlatBufferBuilder &_fbb,
+    const std::vector<flatbuffers::Offset<Object>> *objects = nullptr,
+    const std::vector<flatbuffers::Offset<Enum>> *enums = nullptr,
+    const char *file_ident = nullptr,
+    const char *file_ext = nullptr,
+    flatbuffers::Offset<Object> root_table = 0) {
+  return CreateSchema(_fbb, objects ? _fbb.CreateVector<flatbuffers::Offset<Object>>(*objects) : 0, enums ? _fbb.CreateVector<flatbuffers::Offset<Enum>>(*enums) : 0, file_ident ? _fbb.CreateString(file_ident) : 0, file_ext ? _fbb.CreateString(file_ext) : 0, root_table);
+}
 
-inline const char *SchemaIdentifier() { return "BFBS"; }
+inline const reflection::Schema *GetSchema(const void *buf) {
+  return flatbuffers::GetRoot<reflection::Schema>(buf);
+}
 
-inline bool SchemaBufferHasIdentifier(const void *buf) { return flatbuffers::BufferHasIdentifier(buf, SchemaIdentifier()); }
+inline const char *SchemaIdentifier() {
+  return "BFBS";
+}
 
-inline bool VerifySchemaBuffer(flatbuffers::Verifier &verifier) { return verifier.VerifyBuffer<reflection::Schema>(SchemaIdentifier()); }
+inline bool SchemaBufferHasIdentifier(const void *buf) {
+  return flatbuffers::BufferHasIdentifier(buf, SchemaIdentifier());
+}
+
+inline bool VerifySchemaBuffer(flatbuffers::Verifier &verifier) {
+  return verifier.VerifyBuffer<reflection::Schema>(SchemaIdentifier());
+}
 
 inline const char *SchemaExtension() { return "bfbs"; }
 
-inline void FinishSchemaBuffer(flatbuffers::FlatBufferBuilder &fbb, flatbuffers::Offset<reflection::Schema> root) { fbb.Finish(root, SchemaIdentifier()); }
+inline void FinishSchemaBuffer(flatbuffers::FlatBufferBuilder &fbb, flatbuffers::Offset<reflection::Schema> root) {
+  fbb.Finish(root, SchemaIdentifier());
+}
 
 }  // namespace reflection
 
diff --git a/include/flatbuffers/util.h b/include/flatbuffers/util.h
index 7bd7513..c6755ab 100644
--- a/include/flatbuffers/util.h
+++ b/include/flatbuffers/util.h
@@ -95,20 +95,20 @@
 }
 
 // Portable implementation of strtoll().
-inline int64_t StringToInt(const char *str, int base = 10) {
+inline int64_t StringToInt(const char *str, char **endptr = nullptr, int base = 10) {
   #ifdef _MSC_VER
-    return _strtoi64(str, nullptr, base);
+    return _strtoi64(str, endptr, base);
   #else
-    return strtoll(str, nullptr, base);
+    return strtoll(str, endptr, base);
   #endif
 }
 
 // Portable implementation of strtoull().
-inline int64_t StringToUInt(const char *str, int base = 10) {
+inline int64_t StringToUInt(const char *str, char **endptr = nullptr, int base = 10) {
   #ifdef _MSC_VER
-    return _strtoui64(str, nullptr, base);
+    return _strtoui64(str, endptr, base);
   #else
-    return strtoull(str, nullptr, base);
+    return strtoull(str, endptr, base);
   #endif
 }
 
@@ -276,6 +276,10 @@
   }
   if ((**in << len) & 0x80) return -1;  // Bit after leading 1's must be 0.
   if (!len) return *(*in)++;
+  // UTF-8 encoded values with a length are between 2 and 4 bytes.
+  if (len < 2 || len > 4) {
+    return -1;
+  }
   // Grab initial bits of the code.
   int ucc = *(*in)++ & ((1 << (7 - len)) - 1);
   for (int i = 0; i < len - 1; i++) {
@@ -283,6 +287,32 @@
     ucc <<= 6;
     ucc |= *(*in)++ & 0x3F;  // Grab 6 more bits of the code.
   }
+  // UTF-8 cannot encode values between 0xD800 and 0xDFFF (reserved for
+  // UTF-16 surrogate pairs).
+  if (ucc >= 0xD800 && ucc <= 0xDFFF) {
+    return -1;
+  }
+  // UTF-8 must represent code points in their shortest possible encoding.
+  switch (len) {
+    case 2:
+      // Two bytes of UTF-8 can represent code points from U+0080 to U+07FF.
+      if (ucc < 0x0080 || ucc > 0x07FF) {
+        return -1;
+      }
+      break;
+    case 3:
+      // Three bytes of UTF-8 can represent code points from U+0800 to U+FFFF.
+      if (ucc < 0x0800 || ucc > 0xFFFF) {
+        return -1;
+      }
+      break;
+    case 4:
+      // Four bytes of UTF-8 can represent code points from U+10000 to U+10FFFF.
+      if (ucc < 0x10000 || ucc > 0x10FFFF) {
+        return -1;
+      }
+      break;
+  }
   return ucc;
 }
 
diff --git a/java/com/google/flatbuffers/FlatBufferBuilder.java b/java/com/google/flatbuffers/FlatBufferBuilder.java
index c2186fa..fd4b729 100644
--- a/java/com/google/flatbuffers/FlatBufferBuilder.java
+++ b/java/com/google/flatbuffers/FlatBufferBuilder.java
@@ -367,6 +367,53 @@
     }
     /// @endcond
 
+    /**
+     * Create a new array/vector and return a ByteBuffer to be filled later.
+     * Call {@link #endVector} after this method to get an offset to the beginning
+     * of vector.
+     *
+     * @param elem_size the size of each element in bytes.
+     * @param num_elems number of elements in the vector.
+     * @param alignment byte alignment.
+     * @return ByteBuffer with position and limit set to the space allocated for the array.
+     */
+    public ByteBuffer createUnintializedVector(int elem_size, int num_elems, int alignment) {
+        int length = elem_size * num_elems;
+        startVector(elem_size, num_elems, alignment);
+
+        bb.position(space -= length);
+
+        // Slice and limit the copy vector to point to the 'array'
+        ByteBuffer copy = bb.slice().order(ByteOrder.LITTLE_ENDIAN);
+        copy.limit(length);
+        return copy;
+    }
+
+   /**
+     * Create a vector of tables.
+     *
+     * @param offsets Offsets of the tables.
+     * @return Returns offset of the vector.
+     */
+    public int createVectorOfTables(int[] offsets) {
+        notNested();
+        startVector(Constants.SIZEOF_INT, offsets.length, Constants.SIZEOF_INT);
+        for(int i = offsets.length - 1; i >= 0; i--) addOffset(offsets[i]);
+        return endVector();
+    }
+
+    /**
+     * Create a vector of sorted by the key tables.
+     *
+     * @param obj Instance of the table subclass.
+     * @param offsets Offsets of the tables.
+     * @return Returns offset of the sorted vector.
+     */
+    public <T extends Table> int createSortedVectorOfTables(T obj, int[] offsets) {
+        obj.sortTables(offsets, bb);
+        return createVectorOfTables(offsets);
+    }
+	
    /**
     * Encode the string `s` in the buffer using UTF-8.  If {@code s} is
     * already a {@link CharBuffer}, this method is allocation free.
@@ -413,6 +460,20 @@
         return endVector();
     }
 
+    /**
+     * Create a byte array in the buffer.
+     *
+     * @param arr A source array with data
+     * @return The offset in the buffer where the encoded array starts.
+     */
+    public int createByteVector(byte[] arr) {
+        int length = arr.length;
+        startVector(1, length, 1);
+        bb.position(space -= length);
+        bb.put(arr);
+        return endVector();
+    }
+
    /// @cond FLATBUFFERS_INTERNAL
    /**
     * Should not be accessing the final buffer before it is finished.
diff --git a/java/com/google/flatbuffers/Table.java b/java/com/google/flatbuffers/Table.java
index 4087654..b853842 100644
--- a/java/com/google/flatbuffers/Table.java
+++ b/java/com/google/flatbuffers/Table.java
@@ -37,6 +37,12 @@
       return Charset.forName("UTF-8").newDecoder();
     }
   };
+  public final static ThreadLocal<Charset> UTF8_CHARSET = new ThreadLocal<Charset>() {
+    @Override
+    protected Charset initialValue() {
+      return Charset.forName("UTF-8");
+    }
+  };
   private final static ThreadLocal<CharBuffer> CHAR_BUFFER = new ThreadLocal<CharBuffer>();
   /** Used to hold the position of the `bb` buffer. */
   protected int bb_pos;
@@ -61,6 +67,11 @@
     return vtable_offset < bb.getShort(vtable) ? bb.getShort(vtable + vtable_offset) : 0;
   }
 
+  protected static int __offset(int vtable_offset, int offset, ByteBuffer bb) {
+    int vtable = bb.array().length - offset;
+    return bb.getShort(vtable + vtable_offset - bb.getInt(vtable)) + vtable;
+  }
+
   /**
    * Retrieve a relative offset.
    *
@@ -71,6 +82,10 @@
     return offset + bb.getInt(offset);
   }
 
+  protected static int __indirect(int offset, ByteBuffer bb) {
+    return offset + bb.getInt(offset);
+  }
+
   /**
    * Create a Java `String` from UTF-8 data stored inside the FlatBuffer.
    *
@@ -188,6 +203,76 @@
     }
     return true;
   }
+
+  /**
+   * Sort tables by the key.
+   *
+   * @param offsets An 'int' indexes of the tables into the bb.
+   * @param bb A {@code ByteBuffer} to get the tables.
+   */
+  protected void sortTables(int[] offsets, final ByteBuffer bb) {
+    Integer[] off = new Integer[offsets.length];
+    for (int i = 0; i < offsets.length; i++) off[i] = offsets[i];
+    java.util.Arrays.sort(off, new java.util.Comparator<Integer>() {
+      public int compare(Integer o1, Integer o2) {
+        return keysCompare(o1, o2, bb);
+      }
+    });
+    for (int i = 0; i < offsets.length; i++) offsets[i] = off[i];
+  }
+
+  /**
+   * Compare two tables by the key.
+   *
+   * @param o1 An 'Integer' index of the first key into the bb.
+   * @param o2 An 'Integer' index of the second key into the bb.
+   * @param bb A {@code ByteBuffer} to get the keys.
+   */
+  protected int keysCompare(Integer o1, Integer o2, ByteBuffer bb) { return 0; }
+
+  /**
+   * Compare two strings in the buffer.
+   *
+   * @param offset_1 An 'int' index of the first string into the bb.
+   * @param offset_2 An 'int' index of the second string into the bb.
+   * @param bb A {@code ByteBuffer} to get the strings.
+   */
+  protected static int compareStrings(int offset_1, int offset_2, ByteBuffer bb) {
+    offset_1 += bb.getInt(offset_1);
+    offset_2 += bb.getInt(offset_2);
+    int len_1 = bb.getInt(offset_1);
+    int len_2 = bb.getInt(offset_2);
+    int startPos_1 = offset_1 + SIZEOF_INT;
+    int startPos_2 = offset_2 + SIZEOF_INT;
+    int len = Math.min(len_1, len_2);
+    byte[] bbArray = bb.array();
+    for(int i = 0; i < len; i++) {
+      if (bbArray[i + startPos_1] != bbArray[i + startPos_2])
+        return bbArray[i + startPos_1] - bbArray[i + startPos_2];
+    }
+    return len_1 - len_2;
+  }
+
+  /**
+   * Compare string from the buffer with the 'String' object.
+   *
+   * @param offset_1 An 'int' index of the first string into the bb.
+   * @param key Second string as a byte array.
+   * @param bb A {@code ByteBuffer} to get the first string.
+   */
+  protected static int compareStrings(int offset_1, byte[] key, ByteBuffer bb) {
+    offset_1 += bb.getInt(offset_1);
+    int len_1 = bb.getInt(offset_1);
+    int len_2 = key.length;
+    int startPos_1 = offset_1 + Constants.SIZEOF_INT;
+    int len = Math.min(len_1, len_2);
+    byte[] bbArray = bb.array();
+    for (int i = 0; i < len; i++) {
+      if (bbArray[i + startPos_1] != key[i])
+        return bbArray[i + startPos_1] - key[i];
+    }
+    return len_1 - len_2;
+  }
 }
 
 /// @endcond
diff --git a/js/flatbuffers.js b/js/flatbuffers.js
index 6c3d15c..c1296d5 100644
--- a/js/flatbuffers.js
+++ b/js/flatbuffers.js
@@ -2,6 +2,10 @@
 /// @addtogroup flatbuffers_javascript_api
 /// @{
 /// @cond FLATBUFFERS_INTERNAL
+/**
+ * @const
+ * @namespace
+ */
 var flatbuffers = {};
 
 /**
@@ -71,8 +75,8 @@
 
 /**
  * @constructor
- * @param {number} high
  * @param {number} low
+ * @param {number} high
  */
 flatbuffers.Long = function(low, high) {
   /**
@@ -89,8 +93,8 @@
 };
 
 /**
- * @param {number} high
  * @param {number} low
+ * @param {number} high
  * @returns {flatbuffers.Long}
  */
 flatbuffers.Long.create = function(low, high) {
@@ -125,11 +129,13 @@
  * Create a FlatBufferBuilder.
  *
  * @constructor
- * @param {number=} initial_size
+ * @param {number=} opt_initial_size
  */
-flatbuffers.Builder = function(initial_size) {
-  if (!initial_size) {
-    initial_size = 1024;
+flatbuffers.Builder = function(opt_initial_size) {
+  if (!opt_initial_size) {
+    var initial_size = 1024;
+  } else {
+    var initial_size = opt_initial_size;
   }
 
   /**
@@ -234,9 +240,8 @@
 };
 
 /**
- * Get the ByteBuffer representing the FlatBuffer. Only call this after you've
- * called finish(). The actual data starts at the ByteBuffer's current position,
- * not necessarily at 0.
+ * Get the bytes representing the FlatBuffer. Only call this after you've
+ * called finish().
  *
  * @returns {Uint8Array}
  */
@@ -639,10 +644,11 @@
  * Finalize a buffer, poiting to the given `root_table`.
  *
  * @param {flatbuffers.Offset} root_table
- * @param {string=} file_identifier
+ * @param {string=} opt_file_identifier
  */
-flatbuffers.Builder.prototype.finish = function(root_table, file_identifier) {
-  if (file_identifier) {
+flatbuffers.Builder.prototype.finish = function(root_table, opt_file_identifier) {
+  if (opt_file_identifier) {
+    var file_identifier = opt_file_identifier;
     this.prep(this.minalign, flatbuffers.SIZEOF_INT +
       flatbuffers.FILE_IDENTIFIER_LENGTH);
     if (file_identifier.length != flatbuffers.FILE_IDENTIFIER_LENGTH) {
@@ -1015,10 +1021,10 @@
  * FlatBuffer later on.
  *
  * @param {number} offset
- * @param {flatbuffers.Encoding=} optionalEncoding Defaults to UTF16_STRING
+ * @param {flatbuffers.Encoding=} opt_encoding Defaults to UTF16_STRING
  * @returns {string|Uint8Array}
  */
-flatbuffers.ByteBuffer.prototype.__string = function(offset, optionalEncoding) {
+flatbuffers.ByteBuffer.prototype.__string = function(offset, opt_encoding) {
   offset += this.readInt32(offset);
 
   var length = this.readInt32(offset);
@@ -1027,7 +1033,7 @@
 
   offset += flatbuffers.SIZEOF_INT;
 
-  if (optionalEncoding === flatbuffers.Encoding.UTF8_BYTES) {
+  if (opt_encoding === flatbuffers.Encoding.UTF8_BYTES) {
     return this.bytes_.subarray(offset, offset + length);
   }
 
diff --git a/net/FlatBuffers/ByteBuffer.cs b/net/FlatBuffers/ByteBuffer.cs
index 5fa1ac7..37a2c7e 100755
--- a/net/FlatBuffers/ByteBuffer.cs
+++ b/net/FlatBuffers/ByteBuffer.cs
@@ -14,7 +14,20 @@
  * limitations under the License.
  */
 
-//#define UNSAFE_BYTEBUFFER  // uncomment this line to use faster ByteBuffer
+// There are 2 #defines that have an impact on performance of this ByteBuffer implementation
+//
+//      UNSAFE_BYTEBUFFER 
+//          This will use unsafe code to manipulate the underlying byte array. This
+//          can yield a reasonable performance increase.
+//
+//      BYTEBUFFER_NO_BOUNDS_CHECK
+//          This will disable the bounds check asserts to the byte array. This can
+//          yield a small performance gain in normal code..
+//
+// Using UNSAFE_BYTEBUFFER and BYTEBUFFER_NO_BOUNDS_CHECK together can yield a
+// performance gain of ~15% for some operations, however doing so is potentially 
+// dangerous. Do so at your own risk!
+//
 
 using System;
 
@@ -22,9 +35,6 @@
 {
     /// <summary>
     /// Class to mimic Java's ByteBuffer which is used heavily in Flatbuffers.
-    /// If your execution environment allows unsafe code, you should enable
-    /// unsafe code in your project and #define UNSAFE_BYTEBUFFER to use a
-    /// MUCH faster version of ByteBuffer.
     /// </summary>
     public class ByteBuffer
     {
@@ -126,11 +136,14 @@
         }
 #endif // !UNSAFE_BYTEBUFFER
 
+
         private void AssertOffsetAndLength(int offset, int length)
         {
+            #if !BYTEBUFFER_NO_BOUNDS_CHECK
             if (offset < 0 ||
                 offset > _buffer.Length - length)
                 throw new ArgumentOutOfRangeException();
+            #endif
         }
 
         public void PutSbyte(int offset, sbyte value)
@@ -200,7 +213,6 @@
         public unsafe void PutUlong(int offset, ulong value)
         {
             AssertOffsetAndLength(offset, sizeof(ulong));
-
             fixed (byte* ptr = _buffer)
             {
                 *(ulong*)(ptr + offset) = BitConverter.IsLittleEndian
diff --git a/net/FlatBuffers/FlatBufferBuilder.cs b/net/FlatBuffers/FlatBufferBuilder.cs
index 590e6ac..b6701df 100644
--- a/net/FlatBuffers/FlatBufferBuilder.cs
+++ b/net/FlatBuffers/FlatBufferBuilder.cs
@@ -296,6 +296,18 @@
             return new VectorOffset(Offset);
         }
 
+        /// <summary>
+        /// Creates a vector of tables.
+        /// </summary>
+        /// <param name="offsets">Offsets of the tables.</param>
+        public VectorOffset CreateVectorOfTables<T>(Offset<T>[] offsets) where T : struct
+        {
+            NotNested();
+            StartVector(sizeof(int), offsets.Length, sizeof(int));
+            for (int i = offsets.Length - 1; i >= 0; i--) AddOffset(offsets[i].Value);
+            return EndVector();
+        }
+
         /// @cond FLATBUFFERS_INTENRAL
         public void Nested(int obj)
         {
@@ -582,6 +594,8 @@
         /// </summary>
         /// <remarks>
         /// This is typically only called after you call `Finish()`.
+        /// The actual data starts at the ByteBuffer's current position,
+        /// not necessarily at `0`.
         /// </remarks>
         /// <returns>
         /// Returns the ByteBuffer for this FlatBuffer.
diff --git a/net/FlatBuffers/FlatBuffers.csproj b/net/FlatBuffers/FlatBuffers.csproj
index 3ae938a..2a0cf99 100644
--- a/net/FlatBuffers/FlatBuffers.csproj
+++ b/net/FlatBuffers/FlatBuffers.csproj
@@ -37,6 +37,7 @@
     <Compile Include="ByteBuffer.cs" />
     <Compile Include="FlatBufferBuilder.cs" />
     <Compile Include="FlatBufferConstants.cs" />
+    <Compile Include="IFlatbufferObject.cs" />
     <Compile Include="Offset.cs" />
     <Compile Include="Properties\AssemblyInfo.cs" />
     <Compile Include="Struct.cs" />
diff --git a/net/FlatBuffers/IFlatbufferObject.cs b/net/FlatBuffers/IFlatbufferObject.cs
new file mode 100644
index 0000000..6a15aba
--- /dev/null
+++ b/net/FlatBuffers/IFlatbufferObject.cs
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2014 Google Inc. All rights reserved.
+ *
+ * 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.
+ */
+
+namespace FlatBuffers
+{
+    /// <summary>
+    /// This is the base for both structs and tables.
+    /// </summary>
+    public interface IFlatbufferObject
+    {
+        void __init(int _i, ByteBuffer _bb);
+
+        ByteBuffer ByteBuffer { get; }
+    }
+}
diff --git a/net/FlatBuffers/Offset.cs b/net/FlatBuffers/Offset.cs
index a1524df..2b17cec 100644
--- a/net/FlatBuffers/Offset.cs
+++ b/net/FlatBuffers/Offset.cs
@@ -19,7 +19,7 @@
     /// <summary>
     /// Offset class for typesafe assignments.
     /// </summary>
-    public struct Offset<T> where T : class
+    public struct Offset<T> where T : struct
     {
         public int Value;
         public Offset(int value)
diff --git a/net/FlatBuffers/Struct.cs b/net/FlatBuffers/Struct.cs
index ab16f28..61da32f 100644
--- a/net/FlatBuffers/Struct.cs
+++ b/net/FlatBuffers/Struct.cs
@@ -19,9 +19,9 @@
     /// <summary>
     /// All structs in the generated code derive from this class, and add their own accessors.
     /// </summary>
-    public abstract class Struct
+    public struct Struct
     {
-        protected int bb_pos;
-        protected ByteBuffer bb;
+        public int bb_pos;
+        public ByteBuffer bb;
     }
-}
\ No newline at end of file
+}
diff --git a/net/FlatBuffers/Table.cs b/net/FlatBuffers/Table.cs
index bd5e364..55182b3 100644
--- a/net/FlatBuffers/Table.cs
+++ b/net/FlatBuffers/Table.cs
@@ -20,31 +20,42 @@
 namespace FlatBuffers
 {
     /// <summary>
-    /// All tables in the generated code derive from this class, and add their own accessors.
+    /// All tables in the generated code derive from this struct, and add their own accessors.
     /// </summary>
-    public abstract class Table
+    public struct Table
     {
-        protected int bb_pos;
-        protected ByteBuffer bb;
+        public int bb_pos;
+        public ByteBuffer bb;
 
         public ByteBuffer ByteBuffer { get { return bb; } }
 
         // Look up a field in the vtable, return an offset into the object, or 0 if the field is not
         // present.
-        protected int __offset(int vtableOffset)
+        public int __offset(int vtableOffset)
         {
             int vtable = bb_pos - bb.GetInt(bb_pos);
             return vtableOffset < bb.GetShort(vtable) ? (int)bb.GetShort(vtable + vtableOffset) : 0;
         }
 
+        public static int __offset(int vtableOffset, int offset, ByteBuffer bb)
+        {
+            int vtable = bb.Length - offset;
+            return (int)bb.GetShort(vtable + vtableOffset - bb.GetInt(vtable)) + vtable;
+        }
+
         // Retrieve the relative offset stored at "offset"
-        protected int __indirect(int offset)
+        public int __indirect(int offset)
+        {
+            return offset + bb.GetInt(offset);
+        }
+
+        public static int __indirect(int offset, ByteBuffer bb)
         {
             return offset + bb.GetInt(offset);
         }
 
         // Create a .NET String from UTF-8 data stored inside the flatbuffer.
-        protected string __string(int offset)
+        public string __string(int offset)
         {
             offset += bb.GetInt(offset);
             var len = bb.GetInt(offset);
@@ -53,7 +64,7 @@
         }
 
         // Get the length of a vector whose offset is stored at "offset" in this object.
-        protected int __vector_len(int offset)
+        public int __vector_len(int offset)
         {
             offset += bb_pos;
             offset += bb.GetInt(offset);
@@ -61,7 +72,7 @@
         }
 
         // Get the start of data of a vector whose offset is stored at "offset" in this object.
-        protected int __vector(int offset)
+        public int __vector(int offset)
         {
             offset += bb_pos;
             return offset + bb.GetInt(offset) + sizeof(int);  // data starts after the length
@@ -70,7 +81,8 @@
         // Get the data of a vector whoses offset is stored at "offset" in this object as an
         // ArraySegment&lt;byte&gt;. If the vector is not present in the ByteBuffer,
         // then a null value will be returned.
-        protected ArraySegment<byte>? __vector_as_arraysegment(int offset) {
+        public ArraySegment<byte>? __vector_as_arraysegment(int offset)
+        {
             var o = this.__offset(offset);
             if (0 == o)
             {
@@ -83,15 +95,15 @@
         }
 
         // Initialize any Table-derived type to point to the union at the given offset.
-        protected TTable __union<TTable>(TTable t, int offset) where TTable : Table
+        public T __union<T>(int offset) where T : struct, IFlatbufferObject
         {
             offset += bb_pos;
-            t.bb_pos = offset + bb.GetInt(offset);
-            t.bb = bb;
+            T t = new T();
+            t.__init(offset + bb.GetInt(offset), bb);
             return t;
         }
 
-        protected static bool __has_identifier(ByteBuffer bb, string ident)
+        public static bool __has_identifier(ByteBuffer bb, string ident)
         {
             if (ident.Length != FlatBufferConstants.FileIdentifierLength)
                 throw new ArgumentException("FlatBuffers: file identifier must be length " + FlatBufferConstants.FileIdentifierLength, "ident");
@@ -104,6 +116,38 @@
             return true;
         }
 
+        // Compare strings in the ByteBuffer.
+        public static int CompareStrings(int offset_1, int offset_2, ByteBuffer bb)
+        {
+            offset_1 += bb.GetInt(offset_1);
+            offset_2 += bb.GetInt(offset_2);
+            var len_1 = bb.GetInt(offset_1);
+            var len_2 = bb.GetInt(offset_2);
+            var startPos_1 = offset_1 + sizeof(int);
+            var startPos_2 = offset_2 + sizeof(int);
+            var len = Math.Min(len_1, len_2);
+            byte[] bbArray = bb.Data;
+            for(int i = 0; i < len; i++) {
+                if (bbArray[i + startPos_1] != bbArray[i + startPos_2])
+                    return bbArray[i + startPos_1] - bbArray[i + startPos_2];
+            }
+            return len_1 - len_2;
+        }
 
+        // Compare string from the ByteBuffer with the string object
+        public static int CompareStrings(int offset_1, byte[] key, ByteBuffer bb)
+        {
+            offset_1 += bb.GetInt(offset_1);
+            var len_1 = bb.GetInt(offset_1);
+            var len_2 = key.Length;
+            var startPos_1 = offset_1 + sizeof(int);
+            var len = Math.Min(len_1, len_2);
+            byte[] bbArray = bb.Data;
+            for (int i = 0; i < len; i++) {
+                if (bbArray[i + startPos_1] != key[i])
+                    return bbArray[i + startPos_1] - key[i];
+            }
+            return len_1 - len_2;
+        }
     }
 }
diff --git a/php/FlatbufferBuilder.php b/php/FlatbufferBuilder.php
index fce4a71..5c18bf4 100644
--- a/php/FlatbufferBuilder.php
+++ b/php/FlatbufferBuilder.php
@@ -245,7 +245,7 @@
     public function putLong($x)
     {
         if ($x > PHP_INT_MAX) {
-            throw new \InvalidArgumentException("your platform can't handle long correctly. use 64bit machine.");
+            throw new \InvalidArgumentException("Your platform can't handle long correctly. Use a 64bit machine.");
         }
 
         $this->bb->putLong($this->space -= 8, $x);
@@ -257,7 +257,7 @@
     public function putUlong($x)
     {
         if ($x > PHP_INT_MAX) {
-            throw new \InvalidArgumentException("your platform can't handle ulong correctly. this is php limitations. please wait extension release.");
+            throw new \InvalidArgumentException("Your platform can't handle ulong correctly. This is a php limitation. Please wait for the extension release.");
         }
 
         $this->bb->putUlong($this->space -= 8, $x);
@@ -593,6 +593,10 @@
 
     protected function is_utf8($bytes)
     {
+        if (function_exists('mb_detect_encoding')) {
+            return (bool) mb_detect_encoding($bytes, 'UTF-8', true);
+        }
+    
         $len = strlen($bytes);
         if ($len < 1) {
             /* NOTE: always return 1 when passed string is null */
diff --git a/pom.xml b/pom.xml
index 8e32fee..86d7f53 100644
--- a/pom.xml
+++ b/pom.xml
@@ -5,7 +5,7 @@
   <modelVersion>4.0.0</modelVersion>
   <groupId>com.google.flatbuffers</groupId>
   <artifactId>flatbuffers-java</artifactId>
-  <version>1.3.0-SNAPSHOT</version>
+  <version>1.4.0-SNAPSHOT</version>
   <packaging>bundle</packaging>
   <name>FlatBuffers Java API</name>
   <description>
diff --git a/readme.md b/readme.md
index 3a7f929..8d05c31 100755
--- a/readme.md
+++ b/readme.md
@@ -1,8 +1,12 @@
-![logo](http://google.github.io/flatbuffers/fpl_logo_small.png) FlatBuffers [![Build Status](https://travis-ci.org/google/flatbuffers.svg?branch=master)](https://travis-ci.org/google/flatbuffers) 
+![logo](http://google.github.io/flatbuffers/fpl_logo_small.png) FlatBuffers
 ===========
-**FlatBuffers** is an efficient cross platform serialization library for games and 
-other memory constrained apps. It allows you to directly access serialized data without 
-unpacking/parsing it first, while still having great forwards/backwards compatibility. 
+
+[![Join the chat at https://gitter.im/google/flatbuffers](https://badges.gitter.im/google/flatbuffers.svg)](https://gitter.im/google/flatbuffers?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
+[![Build Status](https://travis-ci.org/google/flatbuffers.svg?branch=master)](https://travis-ci.org/google/flatbuffers) [![Build status](https://ci.appveyor.com/api/projects/status/yg5idd2fnusv1n10?svg=true)](https://ci.appveyor.com/project/gwvo/flatbuffers)
+
+**FlatBuffers** is an efficient cross platform serialization library for games and
+other memory constrained apps. It allows you to directly access serialized data without
+unpacking/parsing it first, while still having great forwards/backwards compatibility.
 
 **Go to our [landing page][] to browse our documentation.**
 
@@ -11,7 +15,7 @@
 * Windows
 * MacOS X
 * Linux
- 
+
 ## Supported programming languages
 * C++
 * C#
@@ -24,7 +28,7 @@
 
 *and many more in progress...*
 
-## Contribution 
+## Contribution
 * [FlatBuffers Google Group][] to discuss FlatBuffers with other developers and users.
 * [FlatBuffers Issues Tracker][] to submit an issue.
 * [stackoverflow.com][] with [`flatbuffers` tag][] for any questions regarding FlatBuffers.
diff --git a/samples/monster_generated.h b/samples/monster_generated.h
index 62a23ad..1833c62 100644
--- a/samples/monster_generated.h
+++ b/samples/monster_generated.h
@@ -11,8 +11,10 @@
 struct Vec3;
 
 struct Monster;
+struct MonsterT;
 
 struct Weapon;
+struct WeaponT;
 
 enum Color {
   Color_Red = 0,
@@ -36,6 +38,21 @@
   Equipment_MAX = Equipment_Weapon
 };
 
+struct EquipmentUnion {
+  Equipment type;
+
+  flatbuffers::NativeTable *table;
+  EquipmentUnion() : type(Equipment_NONE), table(nullptr) {}
+  EquipmentUnion(const EquipmentUnion &);
+  EquipmentUnion &operator=(const EquipmentUnion &);
+  ~EquipmentUnion();
+
+  static flatbuffers::NativeTable *UnPack(const void *union_obj, Equipment type, const flatbuffers::resolver_function_t *resolver);
+  flatbuffers::Offset<void> Pack(flatbuffers::FlatBufferBuilder &_fbb, const flatbuffers::rehasher_function_t *rehasher = nullptr) const;
+
+  WeaponT *AsWeapon() { return type == Equipment_Weapon ? reinterpret_cast<WeaponT *>(table) : nullptr; }
+};
+
 inline const char **EnumNamesEquipment() {
   static const char *names[] = { "NONE", "Weapon", nullptr };
   return names;
@@ -43,6 +60,14 @@
 
 inline const char *EnumNameEquipment(Equipment e) { return EnumNamesEquipment()[static_cast<int>(e)]; }
 
+template<typename T> struct EquipmentTraits {
+  static const Equipment enum_value = Equipment_NONE;
+};
+
+template<> struct EquipmentTraits<Weapon> {
+  static const Equipment enum_value = Equipment_Weapon;
+};
+
 inline bool VerifyEquipment(flatbuffers::Verifier &verifier, const void *union_obj, Equipment type);
 
 MANUALLY_ALIGNED_STRUCT(4) Vec3 FLATBUFFERS_FINAL_CLASS {
@@ -52,6 +77,8 @@
   float z_;
 
  public:
+  Vec3() { memset(this, 0, sizeof(Vec3)); }
+  Vec3(const Vec3 &_o) { memcpy(this, &_o, sizeof(Vec3)); }
   Vec3(float _x, float _y, float _z)
     : x_(flatbuffers::EndianScalar(_x)), y_(flatbuffers::EndianScalar(_y)), z_(flatbuffers::EndianScalar(_z)) { }
 
@@ -64,7 +91,20 @@
 };
 STRUCT_END(Vec3, 12);
 
+struct MonsterT : public flatbuffers::NativeTable {
+  typedef Monster TableType;
+  std::unique_ptr<Vec3> pos;
+  int16_t mana;
+  int16_t hp;
+  std::string name;
+  std::vector<uint8_t> inventory;
+  Color color;
+  std::vector<std::unique_ptr<WeaponT>> weapons;
+  EquipmentUnion equipped;
+};
+
 struct Monster FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
+  typedef MonsterT NativeTableType;
   enum {
     VT_POS = 4,
     VT_MANA = 6,
@@ -112,6 +152,8 @@
            VerifyEquipment(verifier, equipped(), equipped_type()) &&
            verifier.EndTable();
   }
+  MonsterT *UnPack(const flatbuffers::resolver_function_t *resolver = nullptr) const;
+  static flatbuffers::Offset<Monster> Pack(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT* _o, const flatbuffers::rehasher_function_t *_rehasher = nullptr);
 };
 
 struct MonsterBuilder {
@@ -157,7 +199,7 @@
   return builder_.Finish();
 }
 
-inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb,
+inline flatbuffers::Offset<Monster> CreateMonsterDirect(flatbuffers::FlatBufferBuilder &_fbb,
     const Vec3 *pos = 0,
     int16_t mana = 150,
     int16_t hp = 100,
@@ -167,10 +209,19 @@
     const std::vector<flatbuffers::Offset<Weapon>> *weapons = nullptr,
     Equipment equipped_type = Equipment_NONE,
     flatbuffers::Offset<void> equipped = 0) {
-  return CreateMonster(_fbb, pos, mana, hp, name ? 0 : _fbb.CreateString(name), inventory ? 0 : _fbb.CreateVector<uint8_t>(*inventory), color, weapons ? 0 : _fbb.CreateVector<flatbuffers::Offset<Weapon>>(*weapons), equipped_type, equipped);
+  return CreateMonster(_fbb, pos, mana, hp, name ? _fbb.CreateString(name) : 0, inventory ? _fbb.CreateVector<uint8_t>(*inventory) : 0, color, weapons ? _fbb.CreateVector<flatbuffers::Offset<Weapon>>(*weapons) : 0, equipped_type, equipped);
 }
 
+inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT *_o, const flatbuffers::rehasher_function_t *rehasher = nullptr);
+
+struct WeaponT : public flatbuffers::NativeTable {
+  typedef Weapon TableType;
+  std::string name;
+  int16_t damage;
+};
+
 struct Weapon FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
+  typedef WeaponT NativeTableType;
   enum {
     VT_NAME = 4,
     VT_DAMAGE = 6
@@ -186,6 +237,8 @@
            VerifyField<int16_t>(verifier, VT_DAMAGE) &&
            verifier.EndTable();
   }
+  WeaponT *UnPack(const flatbuffers::resolver_function_t *resolver = nullptr) const;
+  static flatbuffers::Offset<Weapon> Pack(flatbuffers::FlatBufferBuilder &_fbb, const WeaponT* _o, const flatbuffers::rehasher_function_t *_rehasher = nullptr);
 };
 
 struct WeaponBuilder {
@@ -210,10 +263,64 @@
   return builder_.Finish();
 }
 
-inline flatbuffers::Offset<Weapon> CreateWeapon(flatbuffers::FlatBufferBuilder &_fbb,
+inline flatbuffers::Offset<Weapon> CreateWeaponDirect(flatbuffers::FlatBufferBuilder &_fbb,
     const char *name = nullptr,
     int16_t damage = 0) {
-  return CreateWeapon(_fbb, name ? 0 : _fbb.CreateString(name), damage);
+  return CreateWeapon(_fbb, name ? _fbb.CreateString(name) : 0, damage);
+}
+
+inline flatbuffers::Offset<Weapon> CreateWeapon(flatbuffers::FlatBufferBuilder &_fbb, const WeaponT *_o, const flatbuffers::rehasher_function_t *rehasher = nullptr);
+
+inline MonsterT *Monster::UnPack(const flatbuffers::resolver_function_t *resolver) const {
+  (void)resolver;
+  auto _o = new MonsterT();
+  { auto _e = pos(); if (_e) _o->pos = std::unique_ptr<Vec3>(new Vec3(*_e)); };
+  { auto _e = mana(); _o->mana = _e; };
+  { auto _e = hp(); _o->hp = _e; };
+  { auto _e = name(); if (_e) _o->name = _e->str(); };
+  { auto _e = inventory(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->inventory.push_back(_e->Get(_i)); } } };
+  { auto _e = color(); _o->color = _e; };
+  { auto _e = weapons(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->weapons.push_back(std::unique_ptr<WeaponT>(_e->Get(_i)->UnPack(resolver))); } } };
+  { auto _e = equipped_type(); _o->equipped.type = _e; };
+  { auto _e = equipped(); if (_e) _o->equipped.table = EquipmentUnion::UnPack(_e, equipped_type(), resolver); };
+  return _o;
+}
+
+inline flatbuffers::Offset<Monster> Monster::Pack(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT* _o, const flatbuffers::rehasher_function_t *_rehasher) {
+  return CreateMonster(_fbb, _o, _rehasher);
+}
+
+inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT *_o, const flatbuffers::rehasher_function_t *rehasher) {
+  (void)rehasher;
+  return CreateMonster(_fbb,
+    _o->pos ? _o->pos.get() : 0,
+    _o->mana,
+    _o->hp,
+    _o->name.size() ? _fbb.CreateString(_o->name) : 0,
+    _o->inventory.size() ? _fbb.CreateVector(_o->inventory) : 0,
+    _o->color,
+    _o->weapons.size() ? _fbb.CreateVector<flatbuffers::Offset<Weapon>>(_o->weapons.size(), [&](size_t i) { return CreateWeapon(_fbb, _o->weapons[i].get(), rehasher); }) : 0,
+    _o->equipped.type,
+    _o->equipped.Pack(_fbb));
+}
+
+inline WeaponT *Weapon::UnPack(const flatbuffers::resolver_function_t *resolver) const {
+  (void)resolver;
+  auto _o = new WeaponT();
+  { auto _e = name(); if (_e) _o->name = _e->str(); };
+  { auto _e = damage(); _o->damage = _e; };
+  return _o;
+}
+
+inline flatbuffers::Offset<Weapon> Weapon::Pack(flatbuffers::FlatBufferBuilder &_fbb, const WeaponT* _o, const flatbuffers::rehasher_function_t *_rehasher) {
+  return CreateWeapon(_fbb, _o, _rehasher);
+}
+
+inline flatbuffers::Offset<Weapon> CreateWeapon(flatbuffers::FlatBufferBuilder &_fbb, const WeaponT *_o, const flatbuffers::rehasher_function_t *rehasher) {
+  (void)rehasher;
+  return CreateWeapon(_fbb,
+    _o->name.size() ? _fbb.CreateString(_o->name) : 0,
+    _o->damage);
 }
 
 inline bool VerifyEquipment(flatbuffers::Verifier &verifier, const void *union_obj, Equipment type) {
@@ -224,13 +331,48 @@
   }
 }
 
-inline const MyGame::Sample::Monster *GetMonster(const void *buf) { return flatbuffers::GetRoot<MyGame::Sample::Monster>(buf); }
+inline flatbuffers::NativeTable *EquipmentUnion::UnPack(const void *union_obj, Equipment type, const flatbuffers::resolver_function_t *resolver) {
+  switch (type) {
+    case Equipment_NONE: return nullptr;
+    case Equipment_Weapon: return reinterpret_cast<const Weapon *>(union_obj)->UnPack(resolver);
+    default: return nullptr;
+  }
+}
 
-inline Monster *GetMutableMonster(void *buf) { return flatbuffers::GetMutableRoot<Monster>(buf); }
+inline flatbuffers::Offset<void> EquipmentUnion::Pack(flatbuffers::FlatBufferBuilder &_fbb, const flatbuffers::rehasher_function_t *rehasher) const {
+  switch (type) {
+    case Equipment_NONE: return 0;
+    case Equipment_Weapon: return CreateWeapon(_fbb, reinterpret_cast<const WeaponT *>(table), rehasher).Union();
+    default: return 0;
+  }
+}
 
-inline bool VerifyMonsterBuffer(flatbuffers::Verifier &verifier) { return verifier.VerifyBuffer<MyGame::Sample::Monster>(nullptr); }
+inline EquipmentUnion::~EquipmentUnion() {
+  switch (type) {
+    case Equipment_Weapon: delete reinterpret_cast<WeaponT *>(table); break;
+    default:;
+  }
+}
 
-inline void FinishMonsterBuffer(flatbuffers::FlatBufferBuilder &fbb, flatbuffers::Offset<MyGame::Sample::Monster> root) { fbb.Finish(root); }
+inline const MyGame::Sample::Monster *GetMonster(const void *buf) {
+  return flatbuffers::GetRoot<MyGame::Sample::Monster>(buf);
+}
+
+inline Monster *GetMutableMonster(void *buf) {
+  return flatbuffers::GetMutableRoot<Monster>(buf);
+}
+
+inline bool VerifyMonsterBuffer(flatbuffers::Verifier &verifier) {
+  return verifier.VerifyBuffer<MyGame::Sample::Monster>(nullptr);
+}
+
+inline void FinishMonsterBuffer(flatbuffers::FlatBufferBuilder &fbb, flatbuffers::Offset<MyGame::Sample::Monster> root) {
+  fbb.Finish(root);
+}
+
+inline std::unique_ptr<MonsterT> UnPackMonster(const void *buf, const flatbuffers::resolver_function_t *resolver = nullptr) {
+  return std::unique_ptr<MonsterT>(GetMonster(buf)->UnPack(resolver));
+}
 
 }  // namespace Sample
 }  // namespace MyGame
diff --git a/samples/sample_text.cpp b/samples/sample_text.cpp
index 557077d..d851120 100644
--- a/samples/sample_text.cpp
+++ b/samples/sample_text.cpp
@@ -46,7 +46,10 @@
   // to ensure it is correct, we now generate text back from the binary,
   // and compare the two:
   std::string jsongen;
-  GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  if (!GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen)) {
+    printf("Couldn't serialize parsed data to JSON!\n");
+    return 1;
+  }
 
   if (jsongen != jsonfile) {
     printf("%s----------------\n%s", jsongen.c_str(), jsonfile.c_str());
diff --git a/src/flatc.cpp b/src/flatc.cpp
index d410718..fae00de 100644
--- a/src/flatc.cpp
+++ b/src/flatc.cpp
@@ -19,7 +19,7 @@
 #include "flatbuffers/util.h"
 #include <limits>
 
-#define FLATC_VERSION "1.3.0 (" __DATE__ ")"
+#define FLATC_VERSION "1.4.0 (" __DATE__ ")"
 
 static void Error(const std::string &err, bool usage = false,
                   bool show_exe_name = true);
@@ -33,6 +33,9 @@
   const char *generator_opt_short;
   const char *generator_opt_long;
   const char *lang_name;
+  bool (*generateGRPC)(const flatbuffers::Parser &parser,
+                       const std::string &path,
+                       const std::string &file_name);
   flatbuffers::IDLOptions::Language lang;
   const char *generator_help;
 
@@ -43,55 +46,60 @@
 
 const Generator generators[] = {
   { flatbuffers::GenerateBinary,   "-b", "--binary", "binary",
+    nullptr,
     flatbuffers::IDLOptions::kMAX,
     "Generate wire format binaries for any data definitions",
     flatbuffers::BinaryMakeRule },
   { flatbuffers::GenerateTextFile, "-t", "--json", "text",
+    nullptr,
     flatbuffers::IDLOptions::kMAX,
     "Generate text output for any data definitions",
     flatbuffers::TextMakeRule },
   { flatbuffers::GenerateCPP,      "-c", "--cpp", "C++",
+    flatbuffers::GenerateCppGRPC,
     flatbuffers::IDLOptions::kMAX,
     "Generate C++ headers for tables/structs",
     flatbuffers::CPPMakeRule },
   { flatbuffers::GenerateGo,       "-g", "--go", "Go",
+    flatbuffers::GenerateGoGRPC,
     flatbuffers::IDLOptions::kGo,
     "Generate Go files for tables/structs",
     flatbuffers::GeneralMakeRule },
   { flatbuffers::GenerateGeneral,  "-j", "--java", "Java",
+    nullptr,
     flatbuffers::IDLOptions::kJava,
     "Generate Java classes for tables/structs",
     flatbuffers::GeneralMakeRule },
   { flatbuffers::GenerateJS,       "-s", "--js", "JavaScript",
+    nullptr,
     flatbuffers::IDLOptions::kMAX,
     "Generate JavaScript code for tables/structs",
     flatbuffers::JSMakeRule },
   { flatbuffers::GenerateGeneral,  "-n", "--csharp", "C#",
+    nullptr,
     flatbuffers::IDLOptions::kCSharp,
     "Generate C# classes for tables/structs",
     flatbuffers::GeneralMakeRule },
   { flatbuffers::GeneratePython,   "-p", "--python", "Python",
+    nullptr,
     flatbuffers::IDLOptions::kMAX,
     "Generate Python files for tables/structs",
     flatbuffers::GeneralMakeRule },
   { flatbuffers::GeneratePhp, nullptr, "--php", "PHP",
+    nullptr,
     flatbuffers::IDLOptions::kMAX,
     "Generate PHP files for tables/structs",
     flatbuffers::GeneralMakeRule },
-  { flatbuffers::GenerateGRPC, nullptr, "--grpc", "GRPC",
-    flatbuffers::IDLOptions::kMAX,
-    "Generate GRPC interfaces",
-    flatbuffers::CPPMakeRule },
 };
 
-const char *program_name = nullptr;
-flatbuffers::Parser *parser = nullptr;
+const char *g_program_name = nullptr;
+flatbuffers::Parser *g_parser = nullptr;
 
 static void Error(const std::string &err, bool usage, bool show_exe_name) {
-  if (show_exe_name) printf("%s: ", program_name);
+  if (show_exe_name) printf("%s: ", g_program_name);
   printf("%s\n", err.c_str());
   if (usage) {
-    printf("usage: %s [OPTION]... FILE... [-- FILE...]\n", program_name);
+    printf("usage: %s [OPTION]... FILE... [-- FILE...]\n", g_program_name);
     for (size_t i = 0; i < sizeof(generators) / sizeof(generators[0]); ++i)
       printf("  %-12s %s %s.\n",
              generators[i].generator_opt_long,
@@ -106,6 +114,9 @@
       "  --version          Print the version number of flatc and exit.\n"
       "  --strict-json      Strict JSON: field names must be / will be quoted,\n"
       "                     no trailing commas in tables/vectors.\n"
+      "  --allow-non-utf8   Pass non-UTF-8 input through parser and emit nonstandard\n"
+      "                     \\x escapes in JSON. (Default is to raise parse error on\n"
+      "                     non-UTF-8 input.)\n"
       "  --defaults-json    Output fields whose value is the default when\n"
       "                     writing JSON\n"
       "  --unknown-json     Allow fields in JSON that are not defined in the\n"
@@ -123,23 +134,42 @@
       "  --gen-onefile      Generate single output file for C#.\n"
       "  --gen-name-strings Generate type name functions for C++.\n"
       "  --escape-proto-ids Disable appending '_' in namespaces names.\n"
+      "  --gen-object-api   Generate an additional object-based API.\n"
+      "  --cpp-ptr-type T   Set object API pointer type (default std::unique_ptr)\n"
       "  --raw-binary       Allow binaries without file_indentifier to be read.\n"
       "                     This may crash flatc given a mismatched schema.\n"
       "  --proto            Input is a .proto, translate to .fbs.\n"
       "  --schema           Serialize schemas instead of JSON (use with -b)\n"
+      "  --conform FILE     Specify a schema the following schemas should be\n"
+      "                     an evolution of. Gives errors if not.\n"
+      "  --conform-includes Include path for the schema given with --conform\n"
+      "    PATH             \n"
       "FILEs may be schemas, or JSON files (conforming to preceding schema)\n"
       "FILEs after the -- must be binary flatbuffer format files.\n"
       "Output files are named using the base file name of the input,\n"
       "and written to the current directory or the path given by -o.\n"
       "example: %s -c -b schema1.fbs schema2.fbs data.json\n",
-      program_name);
+      g_program_name);
   }
-  if (parser) delete parser;
+  if (g_parser) delete g_parser;
   exit(1);
 }
 
+static void ParseFile(flatbuffers::Parser &parser, const std::string &filename,
+                      const std::string &contents,
+                      std::vector<const char *> &include_directories) {
+  auto local_include_directory = flatbuffers::StripFileName(filename);
+  include_directories.push_back(local_include_directory.c_str());
+  include_directories.push_back(nullptr);
+  if (!parser.Parse(contents.c_str(), &include_directories[0],
+                     filename.c_str()))
+    Error(parser.error_, false, false);
+  include_directories.pop_back();
+  include_directories.pop_back();
+}
+
 int main(int argc, const char *argv[]) {
-  program_name = argv[0];
+  g_program_name = argv[0];
   flatbuffers::IDLOptions opts;
   std::string output_path;
   const size_t num_generators = sizeof(generators) / sizeof(generators[0]);
@@ -148,9 +178,12 @@
   bool print_make_rules = false;
   bool raw_binary = false;
   bool schema_binary = false;
+  bool grpc_enabled = false;
   std::vector<std::string> filenames;
   std::vector<const char *> include_directories;
+  std::vector<const char *> conform_include_directories;
   size_t binary_files_from = std::numeric_limits<size_t>::max();
+  std::string conform_to_schema;
   for (int argi = 1; argi < argc; argi++) {
     std::string arg = argv[argi];
     if (arg[0] == '-') {
@@ -162,8 +195,16 @@
       } else if(arg == "-I") {
         if (++argi >= argc) Error("missing path following" + arg, true);
         include_directories.push_back(argv[argi]);
+      } else if(arg == "--conform") {
+        if (++argi >= argc) Error("missing path following" + arg, true);
+        conform_to_schema = argv[argi];
+      } else if (arg == "--conform-includes") {
+        if (++argi >= argc) Error("missing path following" + arg, true);
+        conform_include_directories.push_back(argv[argi]);
       } else if(arg == "--strict-json") {
         opts.strict_json = true;
+      } else if(arg == "--allow-non-utf8") {
+        opts.allow_non_utf8 = true;
       } else if(arg == "--no-js-exports") {
         opts.skip_js_exports = true;
       } else if(arg == "--defaults-json") {
@@ -175,10 +216,17 @@
       } else if(arg == "--scoped-enums") {
         opts.prefixed_enums = false;
         opts.scoped_enums = true;
+      } else if (arg == "--no-union-value-namespacing") {
+        opts.union_value_namespacing = false;
       } else if(arg == "--gen-mutable") {
         opts.mutable_buffer = true;
       } else if(arg == "--gen-name-strings") {
         opts.generate_name_strings = true;
+      } else if(arg == "--gen-object-api") {
+        opts.generate_object_based_api = true;
+      } else if (arg == "--cpp-ptr-type") {
+        if (++argi >= argc) Error("missing type following" + arg, true);
+        opts.cpp_object_api_pointer_type = argv[argi];
       } else if(arg == "--gen-all") {
         opts.generate_all = true;
         opts.include_dependence_headers = false;
@@ -204,6 +252,8 @@
       } else if(arg == "--version") {
         printf("flatc version %s\n", FLATC_VERSION);
         exit(0);
+      } else if(arg == "--grpc") {
+        grpc_enabled = true;
       } else {
         for (size_t i = 0; i < num_generators; ++i) {
           if (arg == generators[i].generator_opt_long ||
@@ -214,7 +264,7 @@
             goto found;
           }
         }
-        Error("unknown commandline argument" + arg, true);
+        Error("unknown commandline argument: " + arg, true);
         found:;
       }
     } else {
@@ -227,12 +277,21 @@
   if (opts.proto_mode) {
     if (any_generator)
       Error("cannot generate code directly from .proto files", true);
-  } else if (!any_generator) {
+  } else if (!any_generator && conform_to_schema.empty()) {
     Error("no options: specify at least one generator.", true);
   }
 
+  flatbuffers::Parser conform_parser;
+  if (!conform_to_schema.empty()) {
+    std::string contents;
+    if (!flatbuffers::LoadFile(conform_to_schema.c_str(), true, &contents))
+      Error("unable to load schema: " + conform_to_schema);
+    ParseFile(conform_parser, conform_to_schema, contents,
+              conform_include_directories);
+  }
+
   // Now process the files:
-  parser = new flatbuffers::Parser(opts);
+  g_parser = new flatbuffers::Parser(opts);
   for (auto file_it = filenames.begin();
             file_it != filenames.end();
           ++file_it) {
@@ -243,8 +302,8 @@
       bool is_binary = static_cast<size_t>(file_it - filenames.begin()) >=
                        binary_files_from;
       if (is_binary) {
-        parser->builder_.Clear();
-        parser->builder_.PushFlatBuffer(
+        g_parser->builder_.Clear();
+        g_parser->builder_.PushFlatBuffer(
           reinterpret_cast<const uint8_t *>(contents.c_str()),
           contents.length());
         if (!raw_binary) {
@@ -253,17 +312,17 @@
           // does not contain a file identifier.
           // We'd expect that typically any binary used as a file would have
           // such an identifier, so by default we require them to match.
-          if (!parser->file_identifier_.length()) {
+          if (!g_parser->file_identifier_.length()) {
             Error("current schema has no file_identifier: cannot test if \"" +
                  *file_it +
                  "\" matches the schema, use --raw-binary to read this file"
                  " anyway.");
           } else if (!flatbuffers::BufferHasIdentifier(contents.c_str(),
-                                             parser->file_identifier_.c_str())) {
+                         g_parser->file_identifier_.c_str())) {
             Error("binary \"" +
                  *file_it +
                  "\" does not have expected file_identifier \"" +
-                 parser->file_identifier_ +
+                 g_parser->file_identifier_ +
                  "\", use --raw-binary to read this file anyway.");
           }
         }
@@ -272,36 +331,34 @@
         if (contents.length() != strlen(contents.c_str())) {
           Error("input file appears to be binary: " + *file_it, true);
         }
-        if (flatbuffers::GetExtension(*file_it) == "fbs") {
+        auto is_schema = flatbuffers::GetExtension(*file_it) == "fbs";
+        if (is_schema) {
           // If we're processing multiple schemas, make sure to start each
           // one from scratch. If it depends on previous schemas it must do
           // so explicitly using an include.
-          delete parser;
-          parser = new flatbuffers::Parser(opts);
+          delete g_parser;
+          g_parser = new flatbuffers::Parser(opts);
         }
-        auto local_include_directory = flatbuffers::StripFileName(*file_it);
-        include_directories.push_back(local_include_directory.c_str());
-        include_directories.push_back(nullptr);
-        if (!parser->Parse(contents.c_str(), &include_directories[0],
-                          file_it->c_str()))
-          Error(parser->error_, false, false);
+        ParseFile(*g_parser, *file_it, contents, include_directories);
+        if (is_schema && !conform_to_schema.empty()) {
+          auto err = g_parser->ConformTo(conform_parser);
+          if (!err.empty()) Error("schemas don\'t conform: " + err);
+        }
         if (schema_binary) {
-          parser->Serialize();
-          parser->file_extension_ = reflection::SchemaExtension();
+          g_parser->Serialize();
+          g_parser->file_extension_ = reflection::SchemaExtension();
         }
-        include_directories.pop_back();
-        include_directories.pop_back();
       }
 
       std::string filebase = flatbuffers::StripPath(
                                flatbuffers::StripExtension(*file_it));
 
       for (size_t i = 0; i < num_generators; ++i) {
-        parser->opts.lang = generators[i].lang;
+        g_parser->opts.lang = generators[i].lang;
         if (generator_enabled[i]) {
           if (!print_make_rules) {
             flatbuffers::EnsureDirExists(output_path);
-            if (!generators[i].generate(*parser, output_path, filebase)) {
+            if (!generators[i].generate(*g_parser, output_path, filebase)) {
               Error(std::string("Unable to generate ") +
                     generators[i].lang_name +
                     " for " +
@@ -309,21 +366,32 @@
             }
           } else {
             std::string make_rule = generators[i].make_rule(
-                *parser, output_path, *file_it);
+                *g_parser, output_path, *file_it);
             if (!make_rule.empty())
               printf("%s\n", flatbuffers::WordWrap(
                   make_rule, 80, " ", " \\").c_str());
           }
+          if (grpc_enabled) {
+            if (generators[i].generateGRPC != nullptr) {
+              if (!generators[i].generateGRPC(*g_parser, output_path, filebase)) {
+                    Error(std::string("Unable to generate GRPC interface for") +
+                          generators[i].lang_name);
+              }
+            } else {
+                Error(std::string("GRPC interface generator not implemented for ") +
+                      generators[i].lang_name);
+            }
+          }
         }
       }
 
-      if (opts.proto_mode) GenerateFBS(*parser, output_path, filebase);
+      if (opts.proto_mode) GenerateFBS(*g_parser, output_path, filebase);
 
       // We do not want to generate code for the definitions in this file
       // in any files coming up next.
-      parser->MarkGenerated();
+      g_parser->MarkGenerated();
   }
 
-  delete parser;
+  delete g_parser;
   return 0;
 }
diff --git a/src/idl_gen_cpp.cpp b/src/idl_gen_cpp.cpp
index ae82164..8681e17 100644
--- a/src/idl_gen_cpp.cpp
+++ b/src/idl_gen_cpp.cpp
@@ -94,7 +94,11 @@
       auto &struct_def = **it;
       if (!struct_def.generated) {
         SetNameSpace(struct_def.defined_namespace, &code);
-        code += "struct " + struct_def.name + ";\n\n";
+        code += "struct " + struct_def.name + ";\n";
+        if (parser_.opts.generate_object_based_api && !struct_def.fixed) {
+          code += "struct " + NativeName(struct_def.name) + ";\n";
+        }
+        code += "\n";
       }
     }
 
@@ -125,6 +129,14 @@
         GenTable(struct_def, &code);
       }
     }
+    for (auto it = parser_.structs_.vec.begin();
+         it != parser_.structs_.vec.end(); ++it) {
+      auto &struct_def = **it;
+      if (!struct_def.fixed && !struct_def.generated) {
+        SetNameSpace(struct_def.defined_namespace, &code);
+        GenTablePost(struct_def, &code);
+      }
+    }
 
     // Generate code for union verifiers.
     for (auto it = parser_.enums_.vec.begin(); it != parser_.enums_.vec.end();
@@ -132,7 +144,7 @@
       auto &enum_def = **it;
       if (enum_def.is_union && !enum_def.generated) {
         SetNameSpace(enum_def.defined_namespace, &code);
-        GenEnumPost(enum_def, &code);
+        GenUnionPost(enum_def, &code);
       }
     }
 
@@ -147,40 +159,40 @@
       // The root datatype accessor:
       code += "inline const " + cpp_qualified_name + " *Get";
       code += name;
-      code += "(const void *buf) { return flatbuffers::GetRoot<";
-      code += cpp_qualified_name + ">(buf); }\n\n";
+      code += "(const void *buf) {\n  return flatbuffers::GetRoot<";
+      code += cpp_qualified_name + ">(buf);\n}\n\n";
       if (parser_.opts.mutable_buffer) {
         code += "inline " + name + " *GetMutable";
         code += name;
-        code += "(void *buf) { return flatbuffers::GetMutableRoot<";
-        code += name + ">(buf); }\n\n";
+        code += "(void *buf) {\n  return flatbuffers::GetMutableRoot<";
+        code += name + ">(buf);\n}\n\n";
       }
 
       if (parser_.file_identifier_.length()) {
         // Return the identifier
         code += "inline const char *" + name;
-        code += "Identifier() { return \"" + parser_.file_identifier_;
-        code += "\"; }\n\n";
+        code += "Identifier() {\n  return \"" + parser_.file_identifier_;
+        code += "\";\n}\n\n";
 
         // Check if a buffer has the identifier.
         code += "inline bool " + name;
-        code += "BufferHasIdentifier(const void *buf) { return flatbuffers::";
+        code += "BufferHasIdentifier(const void *buf) {\n  return flatbuffers::";
         code += "BufferHasIdentifier(buf, ";
-        code += name + "Identifier()); }\n\n";
+        code += name + "Identifier());\n}\n\n";
       }
 
       // The root verifier:
       code += "inline bool Verify";
       code += name;
       code +=
-          "Buffer(flatbuffers::Verifier &verifier) { "
-          "return verifier.VerifyBuffer<";
+          "Buffer(flatbuffers::Verifier &verifier) {\n"
+          "  return verifier.VerifyBuffer<";
       code += cpp_qualified_name + ">(";
       if (parser_.file_identifier_.length())
         code += name + "Identifier()";
       else
         code += "nullptr";
-      code += "); }\n\n";
+      code += ");\n}\n\n";
 
       if (parser_.file_extension_.length()) {
         // Return the extension
@@ -193,10 +205,22 @@
       code += "inline void Finish" + name;
       code +=
           "Buffer(flatbuffers::FlatBufferBuilder &fbb, flatbuffers::Offset<";
-      code += cpp_qualified_name + "> root) { fbb.Finish(root";
+      code += cpp_qualified_name + "> root) {\n  fbb.Finish(root";
       if (parser_.file_identifier_.length())
         code += ", " + name + "Identifier()";
-      code += "); }\n\n";
+      code += ");\n}\n\n";
+
+      if (parser_.opts.generate_object_based_api) {
+        // A convenient root unpack function.
+        auto native_name =
+            NativeName(WrapInNameSpace(*parser_.root_struct_def_));
+        code += "inline " + GenTypeNativePtr(native_name, nullptr, false);
+        code += " UnPack" + name;
+        code += "(const void *buf, const flatbuffers::resolver_function_t *";
+        code += "resolver = nullptr) {\n  return ";
+        code += GenTypeNativePtr(native_name, nullptr, true);
+        code += "(Get" + name + "(buf)->UnPack(resolver));\n}\n\n";
+      }
     }
 
     assert(cur_name_space_);
@@ -229,9 +253,10 @@
   // Return a C++ type from the table in idl.h
   std::string GenTypeBasic(const Type &type, bool user_facing_type) {
     static const char *ctypename[] = {
-#define FLATBUFFERS_TD(ENUM, IDLTYPE, CTYPE, JTYPE, GTYPE, NTYPE, PTYPE) #CTYPE,
+    #define FLATBUFFERS_TD(ENUM, IDLTYPE, CTYPE, JTYPE, GTYPE, NTYPE, PTYPE) \
+            #CTYPE,
         FLATBUFFERS_GEN_TYPES(FLATBUFFERS_TD)
-#undef FLATBUFFERS_TD
+    #undef FLATBUFFERS_TD
     };
     if (user_facing_type) {
       if (type.enum_def) return WrapInNameSpace(*type.enum_def);
@@ -249,9 +274,8 @@
       case BASE_TYPE_VECTOR:
         return "flatbuffers::Vector<" +
                GenTypeWire(type.VectorType(), "", false) + ">";
-      case BASE_TYPE_STRUCT: {
+      case BASE_TYPE_STRUCT:
         return WrapInNameSpace(*type.struct_def);
-      }
       case BASE_TYPE_UNION:
       // fall through
       default:
@@ -278,6 +302,53 @@
                                                      : "flatbuffers::uoffset_t";
   }
 
+  // TODO(wvo): make this configurable.
+  std::string NativeName(const std::string &name) { return name + "T"; }
+
+  const std::string &PtrType(const FieldDef *field) {
+    auto attr = field ? field->attributes.Lookup("cpp_ptr_type") : nullptr;
+    return attr ? attr->constant : parser_.opts.cpp_object_api_pointer_type;
+  }
+
+  std::string GenTypeNativePtr(const std::string &type, const FieldDef *field,
+                               bool is_constructor) {
+    auto &ptr_type = PtrType(field);
+    if (ptr_type == "naked") return is_constructor ? "" : type + " *";
+    return ptr_type + "<" + type + ">";
+  }
+
+  std::string GenPtrGet(const FieldDef &field) {
+    auto &ptr_type = PtrType(&field);
+    return ptr_type == "naked" ? "" : ".get()";
+  }
+
+  std::string GenTypeNative(const Type &type, bool invector,
+                            const FieldDef &field) {
+    switch (type.base_type) {
+      case BASE_TYPE_STRING:
+        return "std::string";
+      case BASE_TYPE_VECTOR:
+        return "std::vector<" + GenTypeNative(type.VectorType(), true, field) +
+               ">";
+      case BASE_TYPE_STRUCT:
+        if (IsStruct(type)) {
+          if (invector || field.native_inline) {
+            return WrapInNameSpace(*type.struct_def);
+          } else {
+            return GenTypeNativePtr(WrapInNameSpace(*type.struct_def), &field,
+                                    false);
+          }
+        } else {
+          return GenTypeNativePtr(NativeName(WrapInNameSpace(*type.struct_def)),
+                                  &field, false);
+        }
+      case BASE_TYPE_UNION:
+        return type.enum_def->name + "Union";
+      default:
+        return GenTypeBasic(type, true);
+    }
+  }
+
   // Return a C++ type for any type (scalar/pointer) specifically for
   // using a flatbuffer.
   std::string GenTypeGet(const Type &type, const char *afterbasic,
@@ -293,15 +364,15 @@
     return (opts.scoped_enums ? "enum class " : "enum ") + enum_def.name;
   }
 
-  static std::string GenEnumVal(const EnumDef &enum_def,
-                                const std::string &enum_val,
-                                const IDLOptions &opts) {
+  static std::string GenEnumValDecl(const EnumDef &enum_def,
+                                    const std::string &enum_val,
+                                    const IDLOptions &opts) {
     return opts.prefixed_enums ? enum_def.name + "_" + enum_val : enum_val;
   }
 
-  static std::string GetEnumVal(const EnumDef &enum_def,
-                                const EnumVal &enum_val,
-                                const IDLOptions &opts) {
+  static std::string GetEnumValUse(const EnumDef &enum_def,
+                                   const EnumVal &enum_val,
+                                   const IDLOptions &opts) {
     if (opts.scoped_enums) {
       return enum_def.name + "::" + enum_val.name;
     } else if (opts.prefixed_enums) {
@@ -311,12 +382,54 @@
     }
   }
 
-  std::string EnumSignature(EnumDef &enum_def) {
+  std::string UnionVerifySignature(EnumDef &enum_def) {
     return "inline bool Verify" + enum_def.name +
-           "(flatbuffers::Verifier &verifier, " + "const void *union_obj, " +
+           "(flatbuffers::Verifier &verifier, const void *union_obj, " +
            enum_def.name + " type)";
   }
 
+  std::string UnionUnPackSignature(EnumDef &enum_def, bool inclass) {
+    return (inclass ? "static " : "") +
+           std::string("flatbuffers::NativeTable *") +
+           (inclass ? "" : enum_def.name + "Union::") +
+           "UnPack(const void *union_obj, " + enum_def.name +
+           " type, const flatbuffers::resolver_function_t *resolver)";
+  }
+
+  std::string UnionPackSignature(EnumDef &enum_def, bool inclass) {
+    return "flatbuffers::Offset<void> " +
+           (inclass ? "" : enum_def.name + "Union::") +
+           "Pack(flatbuffers::FlatBufferBuilder &_fbb, " +
+           "const flatbuffers::rehasher_function_t *rehasher" +
+           (inclass ? " = nullptr" : "") + ") const";
+  }
+
+  std::string TableCreateSignature(StructDef &struct_def, bool predecl) {
+    return "inline flatbuffers::Offset<" + struct_def.name + "> Create" +
+           struct_def.name  +
+           "(flatbuffers::FlatBufferBuilder &_fbb, const " +
+           NativeName(struct_def.name) +
+           " *_o, const flatbuffers::rehasher_function_t *rehasher" +
+           (predecl ? " = nullptr" : "") + ")";
+  }
+
+  std::string TablePackSignature(StructDef &struct_def, bool inclass) {
+    return std::string(inclass ? "static " : "") +
+           "flatbuffers::Offset<" + struct_def.name + "> " +
+           (inclass ? "" : struct_def.name + "::") +
+           "Pack(flatbuffers::FlatBufferBuilder &_fbb, " +
+           "const " + NativeName(struct_def.name) + "* _o, " +
+           "const flatbuffers::rehasher_function_t *_rehasher" +
+           (inclass ? " = nullptr" : "") + ")";
+  }
+
+  std::string TableUnPackSignature(StructDef &struct_def, bool inclass) {
+    return NativeName(struct_def.name) + " *" +
+           (inclass ? "" : struct_def.name + "::") +
+           "UnPack(const flatbuffers::resolver_function_t *resolver" +
+           (inclass ? " = nullptr" : "") + ") const";
+  }
+
   // Generate an enum declaration and an enum string lookup table.
   void GenEnum(EnumDef &enum_def, std::string *code_ptr) {
     std::string &code = *code_ptr;
@@ -331,8 +444,9 @@
          ++it) {
       auto &ev = **it;
       GenComment(ev.doc_comment, code_ptr, nullptr, "  ");
-      code += "  " + GenEnumVal(enum_def, ev.name, parser_.opts) + " = ";
-      code += NumToString(ev.value) + ",\n";
+      code += "  " + GenEnumValDecl(enum_def, ev.name, parser_.opts) + " = ";
+      code += NumToString(ev.value);
+      if (it != enum_def.vals.vec.end() - 1) code += ",\n";
       minv = !minv || minv->value > ev.value ? &ev : minv;
       maxv = !maxv || maxv->value < ev.value ? &ev : maxv;
       anyv |= ev.value;
@@ -341,23 +455,53 @@
       assert(minv && maxv);
       if (enum_def.attributes.Lookup("bit_flags")) {
         if (minv->value != 0)  // If the user didn't defined NONE value
-          code += "  " + GenEnumVal(enum_def, "NONE", parser_.opts) + " = 0,\n";
+          code += ",\n  " + GenEnumValDecl(enum_def, "NONE", parser_.opts) + " = 0";
         if (maxv->value != anyv)  // If the user didn't defined ANY value
-          code += "  " + GenEnumVal(enum_def, "ANY", parser_.opts) + " = " +
-                  NumToString(anyv) + "\n";
+          code += ",\n  " + GenEnumValDecl(enum_def, "ANY", parser_.opts) + " = " +
+                  NumToString(anyv);
       } else {  // MIN & MAX are useless for bit_flags
-        code += "  " + GenEnumVal(enum_def, "MIN", parser_.opts) + " = ";
-        code += GenEnumVal(enum_def, minv->name, parser_.opts) + ",\n";
-        code += "  " + GenEnumVal(enum_def, "MAX", parser_.opts) + " = ";
-        code += GenEnumVal(enum_def, maxv->name, parser_.opts) + "\n";
+        code += ",\n  " + GenEnumValDecl(enum_def, "MIN", parser_.opts) + " = ";
+        code += GenEnumValDecl(enum_def, minv->name, parser_.opts);
+        code += ",\n  " + GenEnumValDecl(enum_def, "MAX", parser_.opts) + " = ";
+        code += GenEnumValDecl(enum_def, maxv->name, parser_.opts);
       }
     }
-    code += "};\n";
+    code += "\n};\n";
     if (parser_.opts.scoped_enums && enum_def.attributes.Lookup("bit_flags"))
       code += "DEFINE_BITMASK_OPERATORS(" + enum_def.name + ", " +
               GenTypeBasic(enum_def.underlying_type, false) + ")\n";
     code += "\n";
 
+    if (parser_.opts.generate_object_based_api && enum_def.is_union) {
+      // Generate a union type
+      code += "struct " + enum_def.name + "Union {\n";
+      code += "  " + enum_def.name + " type;\n\n";
+      code += "  flatbuffers::NativeTable *table;\n";
+      code += "  " + enum_def.name + "Union() : type(";
+      code += GetEnumValUse(enum_def, *enum_def.vals.Lookup("NONE"), parser_.opts);
+      code += "), table(nullptr) {}\n";
+      code += "  " + enum_def.name + "Union(const ";
+      code += enum_def.name + "Union &);\n";
+      code += "  " + enum_def.name + "Union &operator=(const ";
+      code += enum_def.name + "Union &);\n";
+      code += "  ~" + enum_def.name + "Union();\n\n";
+      code += "  " + UnionUnPackSignature(enum_def, true) + ";\n";
+      code += "  " + UnionPackSignature(enum_def, true) + ";\n\n";
+      for (auto it = enum_def.vals.vec.begin(); it != enum_def.vals.vec.end();
+           ++it) {
+        auto &ev = **it;
+        if (ev.value) {
+          auto native_name = NativeName(WrapInNameSpace(*ev.struct_def));
+          code += "  " + native_name + " *As";
+          code += ev.name + "() { return type == ";
+          code += GetEnumValUse(enum_def, ev, parser_.opts);
+          code += " ? reinterpret_cast<" + native_name;
+          code += " *>(table) : nullptr; }\n";
+        }
+      }
+      code += "};\n\n";
+    }
+
     // Generate a generate string table for enum values.
     // Problem is, if values are very sparse that could generate really big
     // tables. Ideally in that case we generate a map lookup instead, but for
@@ -383,38 +527,108 @@
       code += "()[static_cast<int>(e)";
       if (enum_def.vals.vec.front()->value) {
         code += " - static_cast<int>(";
-        code += GetEnumVal(enum_def, *enum_def.vals.vec.front(), parser_.opts) +
+        code += GetEnumValUse(enum_def, *enum_def.vals.vec.front(), parser_.opts) +
                 ")";
       }
       code += "]; }\n\n";
     }
 
+    // Generate type traits for unions to map from a type to union enum value.
     if (enum_def.is_union) {
-      code += EnumSignature(enum_def) + ";\n\n";
+      for (auto it = enum_def.vals.vec.begin();
+        it != enum_def.vals.vec.end();
+        ++it) {
+        auto &ev = **it;
+        if (it == enum_def.vals.vec.begin()) {
+          code += "template<typename T> struct " + enum_def.name + "Traits {\n";
+        }
+        else {
+          code += "template<> struct " + enum_def.name + "Traits<" +
+                  WrapInNameSpace(*ev.struct_def) + "> {\n";
+        }
+        code += "  static const " + enum_def.name + " enum_value = " +
+                GetEnumValUse(enum_def, ev, parser_.opts) + ";\n";
+        code += "};\n\n";
+      }
+    }
+
+    if (enum_def.is_union) {
+      code += UnionVerifySignature(enum_def) + ";\n\n";
     }
   }
 
-  void GenEnumPost(EnumDef &enum_def, std::string *code_ptr_post) {
+  void GenUnionPost(EnumDef &enum_def, std::string *code_ptr) {
     // Generate a verifier function for this union that can be called by the
     // table verifier functions. It uses a switch case to select a specific
     // verifier function to call, this should be safe even if the union type
     // has been corrupted, since the verifiers will simply fail when called
     // on the wrong type.
-    std::string &code_post = *code_ptr_post;
-    code_post += EnumSignature(enum_def) + " {\n  switch (type) {\n";
+    std::string &code = *code_ptr;
+    code += UnionVerifySignature(enum_def) + " {\n  switch (type) {\n";
     for (auto it = enum_def.vals.vec.begin(); it != enum_def.vals.vec.end();
          ++it) {
       auto &ev = **it;
-      code_post += "    case " + GetEnumVal(enum_def, ev, parser_.opts);
+      code += "    case " + GetEnumValUse(enum_def, ev, parser_.opts);
       if (!ev.value) {
-        code_post += ": return true;\n";  // "NONE" enum value.
+        code += ": return true;\n";  // "NONE" enum value.
       } else {
-        code_post += ": return verifier.VerifyTable(reinterpret_cast<const ";
-        code_post += WrapInNameSpace(*ev.struct_def);
-        code_post += " *>(union_obj));\n";
+        code += ": return verifier.VerifyTable(reinterpret_cast<const ";
+        code += WrapInNameSpace(*ev.struct_def);
+        code += " *>(union_obj));\n";
       }
     }
-    code_post += "    default: return false;\n  }\n}\n\n";
+    code += "    default: return false;\n  }\n}\n\n";
+
+    if (parser_.opts.generate_object_based_api) {
+      // Generate a union pack & unpack function.
+      code += "inline " + UnionUnPackSignature(enum_def, false);
+      code += " {\n  switch (type) {\n";
+      for (auto it = enum_def.vals.vec.begin(); it != enum_def.vals.vec.end();
+           ++it) {
+        auto &ev = **it;
+        code += "    case " + GetEnumValUse(enum_def, ev, parser_.opts);
+        if (!ev.value) {
+          code += ": return nullptr;\n";  // "NONE" enum value.
+        } else {
+          code += ": return reinterpret_cast<const ";
+          code += WrapInNameSpace(*ev.struct_def);
+          code += " *>(union_obj)->UnPack(resolver);\n";
+        }
+      }
+      code += "    default: return nullptr;\n  }\n}\n\n";
+      code += "inline " + UnionPackSignature(enum_def, false);
+      code += " {\n  switch (type) {\n";
+      for (auto it = enum_def.vals.vec.begin(); it != enum_def.vals.vec.end();
+           ++it) {
+        auto &ev = **it;
+        code += "    case " + GetEnumValUse(enum_def, ev, parser_.opts);
+        if (!ev.value) {
+          code += ": return 0;\n";  // "NONE" enum value.
+        } else {
+          code += ": return Create" + ev.struct_def->name;
+          code += "(_fbb, reinterpret_cast<const ";
+          code += NativeName(WrapInNameSpace(*ev.struct_def));
+          code += " *>(table), rehasher).Union();\n";
+        }
+      }
+      code += "    default: return 0;\n  }\n}\n\n";
+
+      // Generate a union destructor.
+      code += "inline " + enum_def.name + "Union::~";
+      code += enum_def.name + "Union() {\n";
+      code += "  switch (type) {\n";
+      for (auto it = enum_def.vals.vec.begin(); it != enum_def.vals.vec.end();
+           ++it) {
+        auto &ev = **it;
+        if (ev.value) {
+          code += "    case " + GetEnumValUse(enum_def, ev, parser_.opts);
+          code += ": delete reinterpret_cast<";
+          code += NativeName(WrapInNameSpace(*ev.struct_def));
+          code += " *>(table); break;\n";
+        }
+      }
+      code += "    default:;\n  }\n}\n\n";
+    }
   }
 
   // Generates a value with optionally a cast applied if the field has a
@@ -467,7 +681,7 @@
       if (ev) {
         code += WrapInNameSpace(
             field.value.type.enum_def->defined_namespace,
-            GetEnumVal(*field.value.type.enum_def, *ev, parser_.opts));
+            GetEnumValUse(*field.value.type.enum_def, *ev, parser_.opts));
       } else {
         code += GenUnderlyingCast(field, true, field.value.constant);
       }
@@ -481,12 +695,39 @@
   // Generate an accessor struct, builder structs & function for a table.
   void GenTable(StructDef &struct_def, std::string *code_ptr) {
     std::string &code = *code_ptr;
+
+    if (parser_.opts.generate_object_based_api) {
+      // Generate a C++ object that can hold an unpacked version of this
+      // table.
+      code += "struct " + NativeName(struct_def.name);
+      code += " : public flatbuffers::NativeTable {\n";
+      code += "  typedef " + struct_def.name + " TableType;\n";
+      // Generate GetFullyQualifiedName
+      GenFullyQualifiedNameGetter(NativeName(struct_def.name), code);
+      for (auto it = struct_def.fields.vec.begin();
+           it != struct_def.fields.vec.end(); ++it) {
+        auto &field = **it;
+        if (!field.deprecated &&  // Deprecated fields won't be accessible.
+            field.value.type.base_type != BASE_TYPE_UTYPE) {
+          auto type = GenTypeNative(field.value.type, false, field);
+          auto cpp_type = field.attributes.Lookup("cpp_type");
+          code += "  " + (cpp_type ? cpp_type->constant + " *" : type+ " ") +
+                  field.name + ";\n";
+        }
+      }
+      code += "};\n\n";
+    }
+
     // Generate an accessor struct, with methods of the form:
     // type name() const { return GetField<type>(offset, defaultval); }
     GenComment(struct_def.doc_comment, code_ptr, nullptr);
     code += "struct " + struct_def.name;
     code += " FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table";
     code += " {\n";
+    if (parser_.opts.generate_object_based_api) {
+      code += "  typedef " + NativeName(struct_def.name) +
+              " NativeTableType;\n";
+    }
     // Generate GetFullyQualifiedName
     GenFullyQualifiedNameGetter(struct_def.name, code);
     // Generate field id constants.
@@ -646,7 +887,14 @@
     }
     code += prefix + "verifier.EndTable()";
     code += ";\n  }\n";
-    code += "};\n\n";
+
+    if (parser_.opts.generate_object_based_api) {
+      // Generate the UnPack() pre declaration.
+      code += "  " + TableUnPackSignature(struct_def, true) + ";\n";
+      code += "  " + TablePackSignature(struct_def, true) + ";\n";
+    }
+
+    code += "};\n\n";  // End of table.
 
     // Generate a builder struct, with methods of the form:
     // void add_name(type name) { fbb_.AddElement<type>(offset, name, default);
@@ -727,11 +975,11 @@
     }
     code += "  return builder_.Finish();\n}\n\n";
 
-    // Generate a CreateX function with vector types as parameters
+    // Generate a CreateXDirect function with vector types as parameters
     if (gen_vector_pars) {
       code += "inline flatbuffers::Offset<" + struct_def.name + "> Create";
       code += struct_def.name;
-      code += "(flatbuffers::FlatBufferBuilder &_fbb";
+      code += "Direct(flatbuffers::FlatBufferBuilder &_fbb";
       for (auto it = struct_def.fields.vec.begin();
            it != struct_def.fields.vec.end(); ++it) {
         auto &field = **it;
@@ -757,19 +1005,231 @@
         auto &field = **it;
         if (!field.deprecated) {
           if (field.value.type.base_type == BASE_TYPE_STRING) {
-            code += ", " + field.name + " ? 0 : ";
-            code += "_fbb.CreateString(" + field.name + ")";
+            code += ", " + field.name + " ? ";
+            code += "_fbb.CreateString(" + field.name + ") : 0";
           } else if (field.value.type.base_type == BASE_TYPE_VECTOR) {
-            code += ", " + field.name + " ? 0 : ";
+            code += ", " + field.name + " ? ";
             code += "_fbb.CreateVector<";
             code += GenTypeWire(field.value.type.VectorType(), "", false);
-            code += ">(*" + field.name + ")";
-          } else
+            code += ">(*" + field.name + ") : 0";
+          } else {
             code += ", " + field.name;
+          }
         }
       }
       code += ");\n}\n\n";
     }
+
+    if (parser_.opts.generate_object_based_api) {
+      // Generate a pre-declaration for a CreateX method that works with an
+      // unpacked C++ object.
+      code += TableCreateSignature(struct_def, true) + ";\n\n";
+    }
+  }
+
+  std::string GenUnpackVal(const Type &type, const std::string &val,
+                           bool invector, const FieldDef &afield) {
+    switch (type.base_type) {
+      case BASE_TYPE_STRING:
+        return val + "->str()";
+      case BASE_TYPE_STRUCT:
+        if (IsStruct(type)) {
+          if (invector || afield.native_inline) {
+            return "*" + val;
+          } else {
+            return GenTypeNativePtr(WrapInNameSpace(*type.struct_def),
+                                    &afield, true) +
+                   "(new " +
+                   WrapInNameSpace(*type.struct_def) + "(*" + val + "))";
+          }
+        } else {
+          return GenTypeNativePtr(NativeName(WrapInNameSpace(
+                     *type.struct_def)), &afield, true) +
+                 "(" + val + "->UnPack(resolver))";
+        }
+      default:
+        return val;
+        break;
+    }
+  };
+
+  // Generate code for tables that needs to come after the regular definition.
+  void GenTablePost(StructDef &struct_def, std::string *code_ptr) {
+    std::string &code = *code_ptr;
+
+    if (parser_.opts.generate_object_based_api) {
+      // Generate the UnPack() method.
+      code += "inline " + TableUnPackSignature(struct_def, false) + " {\n";
+      code += "  (void)resolver;\n";
+      code += "  auto _o = new " + NativeName(struct_def.name) + "();\n";
+      for (auto it = struct_def.fields.vec.begin();
+           it != struct_def.fields.vec.end(); ++it) {
+        auto &field = **it;
+        if (!field.deprecated) {
+          auto prefix = "  { auto _e = " + field.name + "(); ";
+          if (!IsScalar(field.value.type.base_type)) prefix += "if (_e) ";
+          auto deref = "_o->";
+          auto dest = deref + field.name;
+          auto assign = prefix + dest + " = ";
+          switch (field.value.type.base_type) {
+            case BASE_TYPE_VECTOR: {
+              code += prefix;
+              code += "{ for (flatbuffers::uoffset_t _i = 0;";
+              code += " _i < _e->size(); _i++) { ";
+              code += dest + ".push_back(";
+              std::string indexing;
+              if (field.value.type.enum_def) {
+                indexing += "(" + field.value.type.enum_def->name + ")";
+              }
+              indexing += "_e->Get(_i)";
+              if (field.value.type.element == BASE_TYPE_BOOL)
+                indexing += "!=0";
+              code += GenUnpackVal(field.value.type.VectorType(),
+                                   indexing, true, field);
+              code += "); } }";
+              break;
+            }
+            case BASE_TYPE_UTYPE: {
+              auto &union_field = **(it + 1);
+              assert(union_field.value.type.base_type == BASE_TYPE_UNION);
+              code += prefix + deref + union_field.name + ".type = _e;";
+              break;
+            }
+            case BASE_TYPE_UNION: {
+              code += prefix + dest + ".table = ";
+              code += field.value.type.enum_def->name;
+              code += "Union::UnPack(_e, ";
+              code += field.name + UnionTypeFieldSuffix() + "(), resolver);";
+              break;
+            }
+            default: {
+              auto cpp_type = field.attributes.Lookup("cpp_type");
+              if (cpp_type) {
+                code += prefix;
+                code += "if (resolver) (*resolver)(reinterpret_cast<void **>(&";
+                code += dest;
+                code += "), static_cast<flatbuffers::hash_value_t>(_e)); else ";
+                code += dest + " = nullptr";
+              } else {
+                code += assign;
+                code += GenUnpackVal(field.value.type, "_e", false, field);
+              }
+              code += ";";
+              break;
+            }
+          }
+          code += " };\n";
+        }
+      }
+      code += "  return _o;\n}\n\n";
+
+      // Generate the X::Pack member function that simply calls the global
+      // CreateX function.
+      code += "inline " + TablePackSignature(struct_def, false) + " {\n";
+      code += "  return Create" + struct_def.name + "(_fbb, _o, _rehasher);\n";
+      code += "}\n\n";
+
+      // Generate a CreateX method that works with an unpacked C++ object.
+      code += TableCreateSignature(struct_def, false) + " {\n";
+      code += "  (void)rehasher;\n";
+      auto before_return_statement = code.size();
+      code += "  return Create";
+      code += struct_def.name + "(_fbb";
+      bool any_fields = false;
+      for (auto it = struct_def.fields.vec.begin();
+           it != struct_def.fields.vec.end(); ++it) {
+        auto &field = **it;
+        if (!field.deprecated) {
+          any_fields = true;
+          auto field_name = field.name;
+          if (field.value.type.base_type == BASE_TYPE_UTYPE) {
+            field_name = field_name.substr(0, field_name.size() -
+                                              strlen(UnionTypeFieldSuffix()));
+            field_name += ".type";
+          }
+          auto accessor = "_o->" + field_name;
+          if (field.attributes.Lookup("cpp_type"))
+            accessor = "rehasher ? static_cast<" +
+                       GenTypeBasic(field.value.type, false) +
+                       ">((*rehasher)(" + accessor + ")) : 0";
+          auto ptrprefix = accessor + " ? ";
+          auto stlprefix = accessor + ".size() ? ";
+          auto postfix = " : 0";
+          if (field.required &&
+              (field.value.type.base_type == BASE_TYPE_STRING ||
+               field.value.type.base_type == BASE_TYPE_VECTOR)) {
+            stlprefix = "";
+            postfix = "";
+          }
+          code += ",\n    ";
+          switch (field.value.type.base_type) {
+            case BASE_TYPE_STRING:
+              code += stlprefix + "_fbb.CreateString(" + accessor + ")";
+              code += postfix;
+              break;
+            case BASE_TYPE_VECTOR: {
+              auto vector_type = field.value.type.VectorType();
+              code += stlprefix;
+              switch (vector_type.base_type) {
+                case BASE_TYPE_STRING:
+                  code += "_fbb.CreateVectorOfStrings(" + accessor + ")";
+                  break;
+                case BASE_TYPE_STRUCT:
+                  if (IsStruct(vector_type)) {
+                    code += "_fbb.CreateVectorOfStructs(" + accessor + ")";
+                  } else {
+                    code += "_fbb.CreateVector<flatbuffers::Offset<";
+                    code += WrapInNameSpace(*vector_type.struct_def) + ">>(" +
+                            accessor;
+                    code += ".size(), [&](size_t i) { return Create";
+                    code += vector_type.struct_def->name + "(_fbb, " + accessor;
+                    code += "[i]" + GenPtrGet(field) + ", rehasher); })";
+                  }
+                  break;
+                case BASE_TYPE_BOOL:
+                  code += "_fbb.CreateVector(" + accessor + ")";
+                  break;
+                default: {
+                  std::string args = accessor;
+                  if (field.value.type.enum_def) {
+                    const std::string basetype = GenTypeBasic(
+                        field.value.type.enum_def->underlying_type, false);
+                    args = "(const " + basetype + "*)" + accessor +
+                           ".data(), " + accessor + ".size()";
+                  }
+                  code += "_fbb.CreateVector(" + args + ")";
+                  break;
+                }
+              }
+              code += postfix;
+              break;
+            }
+            case BASE_TYPE_UNION:
+              code += accessor + ".Pack(_fbb)";
+              break;
+            case BASE_TYPE_STRUCT:
+              if (IsStruct(field.value.type)) {
+                if (field.native_inline) {
+                  code += "&" + accessor;
+                } else {
+                  code += ptrprefix + accessor + GenPtrGet(field) + postfix;
+                }
+              } else {
+                code += ptrprefix + "Create";
+                code += field.value.type.struct_def->name;
+                code += "(_fbb, " + accessor + GenPtrGet(field) + ", rehasher)";
+                code += postfix;
+              }
+              break;
+            default:
+              code += accessor;
+              break;
+          }
+        }
+      }
+      code += ");\n}\n\n";
+      if (!any_fields) code.insert(before_return_statement, "  (void)_o;\n");
+    }
   }
 
   static void GenPadding(const FieldDef &field, std::string &code,
@@ -826,6 +1286,15 @@
     code += "\n public:\n";
     GenFullyQualifiedNameGetter(struct_def.name, code);
 
+    // Generate a default constructor.
+    code += "  " + struct_def.name + "() { memset(this, 0, sizeof(";
+    code += struct_def.name + ")); }\n";
+
+    // Generate a copy constructor.
+    code += "  " + struct_def.name + "(const " + struct_def.name;
+    code += " &_o) { memcpy(this, &_o, sizeof(";
+    code += struct_def.name + ")); }\n";
+
     // Generate a constructor that takes all fields as arguments.
     code += "  " + struct_def.name + "(";
     for (auto it = struct_def.fields.vec.begin();
@@ -928,6 +1397,7 @@
     cur_name_space_ = ns;
   }
 };
+
 }  // namespace cpp
 
 bool GenerateCPP(const Parser &parser, const std::string &path,
diff --git a/src/idl_gen_general.cpp b/src/idl_gen_general.cpp
index 34ca2c3..2d8d83c 100644
--- a/src/idl_gen_general.cpp
+++ b/src/idl_gen_general.cpp
@@ -76,24 +76,28 @@
   IDLOptions::Language language;
   // Whether function names in the language typically start with uppercase.
   bool first_camel_upper;
-  const char *file_extension;
-  const char *string_type;
-  const char *bool_type;
-  const char *open_curly;
-  const char *const_decl;
-  const char *unsubclassable_decl;
-  const char *enum_decl;
-  const char *enum_separator;
-  const char *getter_prefix;
-  const char *getter_suffix;
-  const char *inheritance_marker;
-  const char *namespace_ident;
-  const char *namespace_begin;
-  const char *namespace_end;
-  const char *set_bb_byteorder;
-  const char *get_bb_position;
-  const char *get_fbb_offset;
-  const char *includes;
+  std::string file_extension;
+  std::string string_type;
+  std::string bool_type;
+  std::string open_curly;
+  std::string accessor_type;
+  std::string const_decl;
+  std::string unsubclassable_decl;
+  std::string enum_decl;
+  std::string enum_separator;
+  std::string getter_prefix;
+  std::string getter_suffix;
+  std::string inheritance_marker;
+  std::string namespace_ident;
+  std::string namespace_begin;
+  std::string namespace_end;
+  std::string set_bb_byteorder;
+  std::string get_bb_position;
+  std::string get_fbb_offset;
+  std::string accessor_prefix;
+  std::string accessor_prefix_static;
+  std::string optional_suffix;
+  std::string includes;
   CommentConfig comment_config;
 };
 
@@ -105,6 +109,7 @@
     "String",
     "boolean ",
     " {\n",
+    "class ",
     " final ",
     "final ",
     "final class ",
@@ -118,6 +123,9 @@
     "_bb.order(ByteOrder.LITTLE_ENDIAN); ",
     "position()",
     "offset()",
+    "",
+    "",
+    "",
     "import java.nio.*;\nimport java.lang.*;\nimport java.util.*;\n"
       "import com.google.flatbuffers.*;\n\n@SuppressWarnings(\"unused\")\n",
     {
@@ -133,8 +141,9 @@
     "string",
     "bool ",
     "\n{\n",
+    "struct ",
     " readonly ",
-    "sealed ",
+    "",
     "enum ",
     ",\n",
     " { get",
@@ -146,6 +155,9 @@
     "",
     "Position",
     "Offset",
+    "__p.",
+    "Table.",
+    "?",
     "using System;\nusing FlatBuffers;\n\n",
     {
       nullptr,
@@ -162,6 +174,7 @@
     "string",
     "bool ",
     "\n{\n",
+    "class ",
     "const ",
     " ",
     "class ",
@@ -175,6 +188,9 @@
     "",
     "position()",
     "offset()",
+    "",
+    "",
+    "",
     "import (\n\tflatbuffers \"github.com/google/flatbuffers/go\"\n)",
     {
       nullptr,
@@ -194,16 +210,21 @@
   GeneralGenerator(const Parser &parser, const std::string &path,
                    const std::string &file_name)
       : BaseGenerator(parser, path, file_name, "", "."),
-        lang_(language_parameters[parser_.opts.lang]) {
+        lang_(language_parameters[parser_.opts.lang]),
+        cur_name_space_( nullptr ) {
     assert(parser_.opts.lang <= IDLOptions::kMAX);
       };
+  GeneralGenerator &operator=(const GeneralGenerator &);
   bool generate() {
     std::string one_file_code;
+    cur_name_space_ = parser_.namespaces_.back();
 
     for (auto it = parser_.enums_.vec.begin(); it != parser_.enums_.vec.end();
          ++it) {
       std::string enumcode;
       auto &enum_def = **it;
+      if (!parser_.opts.one_file)
+        cur_name_space_ = enum_def.defined_namespace;
       GenEnum(enum_def, &enumcode);
       if (parser_.opts.one_file) {
         one_file_code += enumcode;
@@ -217,6 +238,8 @@
          it != parser_.structs_.vec.end(); ++it) {
       std::string declcode;
       auto &struct_def = **it;
+      if (!parser_.opts.one_file)
+        cur_name_space_ = struct_def.defined_namespace;
       GenStruct(struct_def, &declcode);
       if (parser_.opts.one_file) {
         one_file_code += declcode;
@@ -235,8 +258,8 @@
 
   // Save out the generated code for a single class while adding
   // declaration boilerplate.
-  bool SaveType(const std::string &defname, const Namespace &ns, 
-  	  const std::string &classcode, bool needs_includes) {
+  bool SaveType(const std::string &defname, const Namespace &ns,
+      const std::string &classcode, bool needs_includes) {
     if (!classcode.length()) return true;
 
     std::string code;
@@ -253,7 +276,7 @@
     return SaveFile(filename.c_str(), code, false);
   }
 
-  const Namespace *CurrentNameSpace() { return parser_.namespaces_.back(); }
+  const Namespace *CurrentNameSpace() { return cur_name_space_; }
 
   std::string FunctionStart(char upper) {
     return std::string() + (lang_.language == IDLOptions::kJava
@@ -342,7 +365,8 @@
                                       const std::string &variable_name)
 {
   if(lang_.language == IDLOptions::kCSharp) {
-    return "new Offset<" + WrapInNameSpace(struct_def) + ">(" + variable_name + ")";
+    return "new Offset<" + WrapInNameSpace(struct_def) + ">(" + variable_name +
+           ")";
   }
   return variable_name;
 }
@@ -400,9 +424,11 @@
 }
 
 // Cast statements for mutator method parameters.
-// In Java, parameters representing unsigned numbers need to be cast down to their respective type.
-// For example, a long holding an unsigned int value would be cast down to int before being put onto the buffer.
-// In C#, one cast directly cast an Enum to its underlying type, which is essential before putting it onto the buffer.
+// In Java, parameters representing unsigned numbers need to be cast down to
+// their respective type. For example, a long holding an unsigned int value
+// would be cast down to int before being put onto the buffer. In C#, one cast
+// directly cast an Enum to its underlying type, which is essential before
+// putting it onto the buffer.
 std::string SourceCast(const Type &type, bool castFromDest) {
   if (type.base_type == BASE_TYPE_VECTOR) {
     return SourceCast(type.VectorType(), castFromDest);
@@ -464,9 +490,21 @@
       return GenEnumDefaultValue(value);
     }
   }
+
+  auto longSuffix = lang_.language == IDLOptions::kJava ? "L" : "";
   switch (value.type.base_type) {
     case BASE_TYPE_FLOAT: return value.constant + "f";
     case BASE_TYPE_BOOL: return value.constant == "0" ? "false" : "true";
+    case BASE_TYPE_ULONG: 
+    {
+      if (lang_.language != IDLOptions::kJava)
+        return value.constant;
+      // Converts the ulong into its bits signed equivalent
+      uint64_t defaultValue = StringToUInt(value.constant.c_str());
+      return NumToString(static_cast<int64_t>(defaultValue)) + longSuffix;
+    }
+    case BASE_TYPE_UINT:
+    case BASE_TYPE_LONG: return value.constant + longSuffix;
     default: return value.constant;
   }
 }
@@ -483,7 +521,8 @@
         case BASE_TYPE_STRING:
           return "default(StringOffset)";
         case BASE_TYPE_STRUCT:
-          return "default(Offset<" + WrapInNameSpace(*value.type.struct_def) + ">)";
+          return "default(Offset<" + WrapInNameSpace(*value.type.struct_def) +
+                 ">)";
         case BASE_TYPE_VECTOR:
           return "default(VectorOffset)";
         default:
@@ -512,7 +551,8 @@
   GenComment(enum_def.doc_comment, code_ptr, &lang_.comment_config);
   code += std::string("public ") + lang_.enum_decl + enum_def.name;
   if (lang_.language == IDLOptions::kCSharp) {
-    code += lang_.inheritance_marker + GenTypeBasic(enum_def.underlying_type, false);
+    code += lang_.inheritance_marker +
+            GenTypeBasic(enum_def.underlying_type, false);
   }
   code += lang_.open_curly;
   if (lang_.language == IDLOptions::kJava) {
@@ -577,12 +617,13 @@
 // Returns the function name that is able to read a value of the given type.
 std::string GenGetter(const Type &type) {
   switch (type.base_type) {
-    case BASE_TYPE_STRING: return "__string";
-    case BASE_TYPE_STRUCT: return "__struct";
-    case BASE_TYPE_UNION:  return "__union";
+    case BASE_TYPE_STRING: return lang_.accessor_prefix + "__string";
+    case BASE_TYPE_STRUCT: return lang_.accessor_prefix + "__struct";
+    case BASE_TYPE_UNION:  return lang_.accessor_prefix + "__union";
     case BASE_TYPE_VECTOR: return GenGetter(type.VectorType());
     default: {
-      std::string getter = "bb." + FunctionStart('G') + "et";
+      std::string getter =
+        lang_.accessor_prefix + "bb." + FunctionStart('G') + "et";
       if (type.base_type == BASE_TYPE_BOOL) {
         getter = "0!=" + getter;
       } else if (GenTypeBasic(type, false) != "byte") {
@@ -597,7 +638,8 @@
 // Hence a setter method will only be generated for such fields.
 std::string GenSetter(const Type &type) {
   if (IsScalar(type.base_type)) {
-    std::string setter = "bb." + FunctionStart('P') + "ut";
+    std::string setter =
+      lang_.accessor_prefix + "bb." + FunctionStart('P') + "ut";
     if (GenTypeBasic(type, false) != "byte" &&
         type.base_type != BASE_TYPE_BOOL) {
       setter += MakeCamel(GenTypeBasic(type, false));
@@ -617,7 +659,8 @@
 
 // Recursively generate arguments for a constructor, to deal with nested
 // structs.
-void GenStructArgs(const StructDef &struct_def, std::string *code_ptr, const char *nameprefix) {
+void GenStructArgs(const StructDef &struct_def, std::string *code_ptr,
+                   const char *nameprefix) {
   std::string &code = *code_ptr;
   for (auto it = struct_def.fields.vec.begin();
        it != struct_def.fields.vec.end();
@@ -642,7 +685,8 @@
 // Recusively generate struct construction statements of the form:
 // builder.putType(name);
 // and insert manual padding.
-void GenStructBody(const StructDef &struct_def, std::string *code_ptr, const char *nameprefix) {
+void GenStructBody(const StructDef &struct_def, std::string *code_ptr,
+                   const char *nameprefix) {
   std::string &code = *code_ptr;
   code += "    builder." + FunctionStart('P') + "rep(";
   code += NumToString(struct_def.minalign) + ", ";
@@ -668,6 +712,90 @@
   }
 }
 
+std::string GenByteBufferLength(const char *bb_name) {
+  std::string bb_len = bb_name;
+  if (lang_.language == IDLOptions::kCSharp) bb_len += ".Length";
+  else bb_len += ".array().length";
+  return bb_len;
+}
+
+std::string GenOffsetGetter(flatbuffers::FieldDef *key_field,
+                            const char *num = nullptr) {
+  std::string key_offset = "";
+  key_offset += lang_.accessor_prefix_static + "__offset(" +
+    NumToString(key_field->value.offset) + ", ";
+  if (num) {
+    key_offset += num;
+    key_offset += (lang_.language == IDLOptions::kCSharp ?
+      ".Value, builder.DataBuffer)" : ", _bb)");
+  } else {
+    key_offset += GenByteBufferLength("bb");
+    key_offset += " - tableOffset, bb)";
+  }
+  return key_offset;
+}
+
+std::string GenLookupKeyGetter(flatbuffers::FieldDef *key_field) {
+  std::string key_getter = "      ";
+  key_getter += "int tableOffset = " + lang_.accessor_prefix_static;
+  key_getter += "__indirect(vectorLocation + 4 * (start + middle)";
+  key_getter += ", bb);\n      ";
+  if (key_field->value.type.base_type == BASE_TYPE_STRING) {
+    key_getter += "int comp = " + lang_.accessor_prefix_static;
+    key_getter += FunctionStart('C') + "ompareStrings(";
+    key_getter += GenOffsetGetter(key_field);
+    key_getter += ", byteKey, bb);\n";
+  } else {
+    auto get_val = GenGetter(key_field->value.type) +
+      "(" + GenOffsetGetter(key_field) + ")";
+    if (lang_.language == IDLOptions::kCSharp) {
+      key_getter += "int comp = " + get_val + ".CompareTo(key);\n";
+    } else {
+      key_getter += GenTypeGet(key_field->value.type) + " val = ";
+      key_getter += get_val + ";\n";
+      key_getter += "      int comp = val > key ? 1 : val < key ? -1 : 0;\n";
+    }
+  }
+  return key_getter;
+}
+
+
+std::string GenKeyGetter(flatbuffers::FieldDef *key_field) {
+  std::string key_getter = "";
+  auto data_buffer = (lang_.language == IDLOptions::kCSharp) ?
+    "builder.DataBuffer" : "_bb";
+  if (key_field->value.type.base_type == BASE_TYPE_STRING) {
+    if (lang_.language == IDLOptions::kJava)
+      key_getter += " return ";
+    key_getter += lang_.accessor_prefix_static;
+    key_getter += FunctionStart('C') + "ompareStrings(";
+    key_getter += GenOffsetGetter(key_field, "o1") + ", ";
+    key_getter += GenOffsetGetter(key_field, "o2") + ", " + data_buffer + ")";
+    if (lang_.language == IDLOptions::kJava)
+      key_getter += ";";
+  }
+  else {
+    auto field_getter = data_buffer + GenGetter(key_field->value.type).substr(2) +
+      "(" + GenOffsetGetter(key_field, "o1") + ")";
+    if (lang_.language == IDLOptions::kCSharp) {
+      key_getter += field_getter;
+      field_getter = data_buffer + GenGetter(key_field->value.type).substr(2) +
+        "(" + GenOffsetGetter(key_field, "o2") + ")";
+      key_getter += ".CompareTo(" + field_getter + ")";
+    }
+    else {
+      key_getter += "\n    " + GenTypeGet(key_field->value.type) + " val_1 = ";
+      key_getter += field_getter + ";\n    " + GenTypeGet(key_field->value.type);
+      key_getter += " val_2 = ";
+      field_getter = data_buffer + GenGetter(key_field->value.type).substr(2) +
+        "(" + GenOffsetGetter(key_field, "o2") + ")";
+      key_getter += field_getter + ";\n";
+      key_getter += "    return val_1 > val_2 ? 1 : val_1 < val_2 ? -1 : 0;\n ";
+    }
+  }
+  return key_getter;
+}
+
 void GenStruct(StructDef &struct_def, std::string *code_ptr) {
   if (struct_def.generated) return;
   std::string &code = *code_ptr;
@@ -684,18 +812,32 @@
       struct_def.attributes.Lookup("csharp_partial")) {
     // generate a partial class for this C# struct/table
     code += "partial ";
-  }
-  else {
+  } else {
     code += lang_.unsubclassable_decl;
   }
-  code += "class " + struct_def.name + lang_.inheritance_marker;
-  code += struct_def.fixed ? "Struct" : "Table";
-  code += " {\n";
+  code += lang_.accessor_type + struct_def.name;
+  if (lang_.language == IDLOptions::kCSharp) {
+    code += " : IFlatbufferObject";
+    code += lang_.open_curly;
+    code += "  private ";
+    code += struct_def.fixed ? "Struct" : "Table";
+    code += " __p;\n";
+
+    if (lang_.language == IDLOptions::kCSharp) {
+        code += "  public ByteBuffer ByteBuffer { get { return __p.bb; } }\n";
+    }
+
+  } else {
+    code += lang_.inheritance_marker;
+    code += struct_def.fixed ? "Struct" : "Table";
+    code += lang_.open_curly;
+  }
   if (!struct_def.fixed) {
     // Generate a special accessor for the table that when used as the root
     // of a FlatBuffer
     std::string method_name = FunctionStart('G') + "etRootAs" + struct_def.name;
-    std::string method_signature = "  public static " + struct_def.name + " " + method_name;
+    std::string method_signature = "  public static " + struct_def.name + " " +
+                                   method_name;
 
     // create convenience method that doesn't require an existing object
     code += method_signature + "(ByteBuffer _bb) ";
@@ -704,8 +846,7 @@
     // create method that allows object reuse
     code += method_signature + "(ByteBuffer _bb, " + struct_def.name + " obj) { ";
     code += lang_.set_bb_byteorder;
-    code += "return (obj.__init(_bb." + FunctionStart('G');
-    code += "etInt(_bb.";
+    code += "return (obj.__assign(_bb." + FunctionStart('G') + "etInt(_bb.";
     code += lang_.get_bb_position;
     code += ") + _bb.";
     code += lang_.get_bb_position;
@@ -716,16 +857,19 @@
         code += "  public static ";
         code += lang_.bool_type + struct_def.name;
         code += "BufferHasIdentifier(ByteBuffer _bb) { return ";
-        code += "__has_identifier(_bb, \"" + parser_.file_identifier_;
+        code += lang_.accessor_prefix_static + "__has_identifier(_bb, \"";
+        code += parser_.file_identifier_;
         code += "\"); }\n";
       }
     }
   }
   // Generate the __init method that sets the field in a pre-existing
   // accessor object. This is to allow object reuse.
-  code += "  public " + struct_def.name;
-  code += " __init(int _i, ByteBuffer _bb) ";
-  code += "{ bb_pos = _i; bb = _bb; return this; }\n\n";
+  code += "  public void __init(int _i, ByteBuffer _bb) ";
+  code += "{ " + lang_.accessor_prefix + "bb_pos = _i; ";
+  code += lang_.accessor_prefix + "bb = _bb; }\n";
+  code += "  public " + struct_def.name + " __assign(int _i, ByteBuffer _bb) ";
+  code += "{ __init(_i, _bb); return this; }\n\n";
   for (auto it = struct_def.fields.vec.begin();
        it != struct_def.fields.vec.end();
        ++it) {
@@ -734,28 +878,35 @@
     GenComment(field.doc_comment, code_ptr, &lang_.comment_config, "  ");
     std::string type_name = GenTypeGet(field.value.type);
     std::string type_name_dest = GenTypeNameDest(field.value.type);
+    std::string conditional_cast = "";
+    std::string optional = "";
+    if (lang_.language == IDLOptions::kCSharp &&
+        !struct_def.fixed &&
+        (field.value.type.base_type == BASE_TYPE_STRUCT ||
+         field.value.type.base_type == BASE_TYPE_UNION ||
+         (field.value.type.base_type == BASE_TYPE_VECTOR &&
+          field.value.type.element == BASE_TYPE_STRUCT))) {
+      optional = lang_.optional_suffix;
+      conditional_cast = "(" + type_name_dest + optional + ")";
+    }
     std::string dest_mask = DestinationMask(field.value.type, true);
     std::string dest_cast = DestinationCast(field.value.type);
     std::string src_cast = SourceCast(field.value.type);
-    std::string method_start = "  public " + type_name_dest + " " +
+    std::string method_start = "  public " + type_name_dest + optional + " " +
                                MakeCamel(field.name, lang_.first_camel_upper);
+    std::string obj = lang_.language == IDLOptions::kCSharp
+      ? "(new " + type_name + "())"
+      : "obj";
 
     // Most field accessors need to retrieve and test the field offset first,
     // this is the prefix code for that:
-    auto offset_prefix = " { int o = __offset(" +
-      NumToString(field.value.offset) +
-      "); return o != 0 ? ";
+    auto offset_prefix = " { int o = " + lang_.accessor_prefix + "__offset(" +
+                         NumToString(field.value.offset) +
+                         "); return o != 0 ? ";
     // Generate the accessors that don't do object reuse.
     if (field.value.type.base_type == BASE_TYPE_STRUCT) {
       // Calls the accessor that takes an accessor object with a new object.
-      if (lang_.language == IDLOptions::kCSharp) {
-        code += method_start + " { get { return Get";
-        code += MakeCamel(field.name, lang_.first_camel_upper);
-        code += "(new ";
-        code += type_name + "()); } }\n";
-        method_start = "  public " + type_name_dest + " Get" + MakeCamel(field.name, lang_.first_camel_upper);
-      }
-      else {
+      if (lang_.language != IDLOptions::kCSharp) {
         code += method_start + "() { return ";
         code += MakeCamel(field.name, lang_.first_camel_upper);
         code += "(new ";
@@ -765,24 +916,16 @@
                field.value.type.element == BASE_TYPE_STRUCT) {
       // Accessors for vectors of structs also take accessor objects, this
       // generates a variant without that argument.
-      if (lang_.language == IDLOptions::kCSharp) {
-        method_start = "  public " + type_name_dest + " Get" + MakeCamel(field.name, lang_.first_camel_upper);
-        code += method_start + "(int j) { return Get";
-      } else {
+      if (lang_.language != IDLOptions::kCSharp) {
         code += method_start + "(int j) { return ";
-      }
-      code += MakeCamel(field.name, lang_.first_camel_upper);
-      code += "(new ";
-      code += type_name + "(), j); }\n";
-    } else if (field.value.type.base_type == BASE_TYPE_VECTOR) {
-      if (lang_.language == IDLOptions::kCSharp) {
-        method_start = "  public " + type_name_dest + " Get" + MakeCamel(field.name, lang_.first_camel_upper);
+        code += MakeCamel(field.name, lang_.first_camel_upper);
+        code += "(new " + type_name + "(), j); }\n";
       }
     } else if (field.value.type.base_type == BASE_TYPE_UNION) {
       if (lang_.language == IDLOptions::kCSharp) {
-        // union types in C# use generic Table-derived type for better type safety
-        method_start = "  public " + type_name_dest + " Get" + MakeCamel(field.name, lang_.first_camel_upper) + "<TTable>";
-        offset_prefix = " where TTable : Table" + offset_prefix;
+        // Union types in C# use generic Table-derived type for better type
+        // safety.
+        method_start += "<TTable>";
         type_name = type_name_dest;
       }
     }
@@ -792,64 +935,78 @@
     // only create default casts for c# scalars or vectors of scalars
     if (lang_.language == IDLOptions::kCSharp &&
         (IsScalar(field.value.type.base_type) ||
-         (field.value.type.base_type == BASE_TYPE_VECTOR && IsScalar(field.value.type.element)))) {
-      // For scalars, default value will be returned by GetDefaultValue(). If the scalar is an enum, GetDefaultValue()
-      // returns an actual c# enum that doesn't need to be casted. However, default values for enum elements of
-      // vectors are integer literals ("0") and are still casted for clarity.
-      if (field.value.type.enum_def == nullptr || field.value.type.base_type == BASE_TYPE_VECTOR) {
+         (field.value.type.base_type == BASE_TYPE_VECTOR &&
+          IsScalar(field.value.type.element)))) {
+      // For scalars, default value will be returned by GetDefaultValue().
+      // If the scalar is an enum, GetDefaultValue() returns an actual c# enum
+      // that doesn't need to be casted. However, default values for enum
+      // elements of vectors are integer literals ("0") and are still casted
+      // for clarity.
+      if (field.value.type.enum_def == nullptr ||
+          field.value.type.base_type == BASE_TYPE_VECTOR) {
           default_cast = "(" + type_name_dest + ")";
       }
     }
-    std::string member_suffix = "";
+    std::string member_suffix = "; ";
     if (IsScalar(field.value.type.base_type)) {
       code += lang_.getter_prefix;
-      member_suffix = lang_.getter_suffix;
+      member_suffix += lang_.getter_suffix;
       if (struct_def.fixed) {
         code += " { return " + getter;
-        code += "(bb_pos + " + NumToString(field.value.offset) + ")";
+        code += "(" + lang_.accessor_prefix + "bb_pos + ";
+        code += NumToString(field.value.offset) + ")";
         code += dest_mask;
       } else {
         code += offset_prefix + getter;
-        code += "(o + bb_pos)" + dest_mask + " : " + default_cast;
+        code += "(o + " + lang_.accessor_prefix + "bb_pos)" + dest_mask;
+        code += " : " + default_cast;
         code += GenDefaultValue(field.value);
       }
     } else {
       switch (field.value.type.base_type) {
         case BASE_TYPE_STRUCT:
-          code += "(" + type_name + " obj";
-          if (struct_def.fixed) {
-            code += ") { return obj.__init(bb_pos + ";
-            code += NumToString(field.value.offset) + ", bb)";
+          if (lang_.language != IDLOptions::kCSharp) {
+            code += "(" + type_name + " obj" + ")";
           } else {
-            code += ")";
-            code += offset_prefix;
-            code += "obj.__init(";
+            code += lang_.getter_prefix;
+            member_suffix += lang_.getter_suffix;
+          }
+          if (struct_def.fixed) {
+            code += " { return " + obj + ".__assign(" + lang_.accessor_prefix;
+            code += "bb_pos + " + NumToString(field.value.offset) + ", ";
+            code += lang_.accessor_prefix + "bb)";
+          } else {
+            code += offset_prefix + conditional_cast;
+            code += obj + ".__assign(";
             code += field.value.type.struct_def->fixed
-                      ? "o + bb_pos"
-                      : "__indirect(o + bb_pos)";
-            code += ", bb) : null";
+                      ? "o + " + lang_.accessor_prefix + "bb_pos"
+                      : lang_.accessor_prefix + "__indirect(o + " +
+                        lang_.accessor_prefix + "bb_pos)";
+            code += ", " + lang_.accessor_prefix + "bb) : null";
           }
           break;
         case BASE_TYPE_STRING:
           code += lang_.getter_prefix;
-          member_suffix = lang_.getter_suffix;
-          code += offset_prefix + getter + "(o + bb_pos) : null";
+          member_suffix += lang_.getter_suffix;
+          code += offset_prefix + getter + "(o + " + lang_.accessor_prefix;
+          code += "bb_pos) : null";
           break;
         case BASE_TYPE_VECTOR: {
           auto vectortype = field.value.type.VectorType();
           code += "(";
           if (vectortype.base_type == BASE_TYPE_STRUCT) {
-            code += type_name + " obj, ";
-            getter = "obj.__init";
+            if (lang_.language != IDLOptions::kCSharp)
+              code += type_name + " obj, ";
+            getter = obj + ".__assign";
           }
-          code += "int j)" + offset_prefix + getter +"(";
-          auto index = "__vector(o) + j * " +
+          code += "int j)" + offset_prefix + conditional_cast + getter +"(";
+          auto index = lang_.accessor_prefix + "__vector(o) + j * " +
                        NumToString(InlineSize(vectortype));
           if (vectortype.base_type == BASE_TYPE_STRUCT) {
             code += vectortype.struct_def->fixed
                       ? index
-                      : "__indirect(" + index + ")";
-            code += ", bb";
+                      : lang_.accessor_prefix + "__indirect(" + index + ")";
+            code += ", " + lang_.accessor_prefix + "bb";
           } else {
             code += index;
           }
@@ -860,14 +1017,19 @@
           break;
         }
         case BASE_TYPE_UNION:
-          code += "(" + type_name + " obj)" + offset_prefix + getter;
-          code += "(obj, o) : null";
+          if (lang_.language == IDLOptions::kCSharp) {
+            code += "() where TTable : struct, IFlatbufferObject";
+            code += offset_prefix + "(TTable?)" + getter;
+            code += "<TTable>(o) : null";
+          } else {
+            code += "(" + type_name + " obj)" + offset_prefix + getter;
+            code += "(obj, o) : null";
+          }
           break;
         default:
           assert(0);
       }
     }
-    code += "; ";
     code += member_suffix;
     code += "}\n";
     if (field.value.type.base_type == BASE_TYPE_VECTOR) {
@@ -875,7 +1037,7 @@
       code += "Length";
       code += lang_.getter_prefix;
       code += offset_prefix;
-      code += "__vector_len(o) : 0; ";
+      code += lang_.accessor_prefix + "__vector_len(o) : 0; ";
       code += lang_.getter_suffix;
       code += "}\n";
     }
@@ -887,16 +1049,19 @@
         case IDLOptions::kJava:
           code += "  public ByteBuffer ";
           code += MakeCamel(field.name, lang_.first_camel_upper);
-          code += "AsByteBuffer() { return __vector_as_bytebuffer(";
+          code += "AsByteBuffer() { return ";
+          code += lang_.accessor_prefix + "__vector_as_bytebuffer(";
           code += NumToString(field.value.offset) + ", ";
-          code += NumToString(field.value.type.base_type == BASE_TYPE_STRING ? 1 :
-                              InlineSize(field.value.type.VectorType()));
+          code += NumToString(field.value.type.base_type == BASE_TYPE_STRING
+                              ? 1
+                              : InlineSize(field.value.type.VectorType()));
           code += "); }\n";
           break;
         case IDLOptions::kCSharp:
           code += "  public ArraySegment<byte>? Get";
           code += MakeCamel(field.name, lang_.first_camel_upper);
-          code += "Bytes() { return __vector_as_arraysegment(";
+          code += "Bytes() { return ";
+          code += lang_.accessor_prefix + "__vector_as_arraysegment(";
           code += NumToString(field.value.offset);
           code += "); }\n";
           break;
@@ -916,30 +1081,49 @@
     auto getNestedMethodName = nestedMethodName;
     if (lang_.language == IDLOptions::kCSharp) {
       getNestedMethodName = "Get" + nestedMethodName;
+      conditional_cast = "(" + nested_type_name + lang_.optional_suffix + ")";
     }
-    code += "  public " + nested_type_name + " ";
-    code += nestedMethodName + "() { return ";
-    code += getNestedMethodName + "(new " + nested_type_name + "()); }\n";
-    code += "  public " + nested_type_name + " " + getNestedMethodName;
-    code += "(" + nested_type_name + " obj) { ";
-    code += "int o = __offset(" + NumToString(field.value.offset) +"); ";
-    code += "return o != 0 ? obj.__init(__indirect(__vector(o)), bb) : null; }\n";
+    if (lang_.language != IDLOptions::kCSharp) {
+      code += "  public " + nested_type_name + lang_.optional_suffix + " ";
+      code += nestedMethodName + "() { return ";
+      code += getNestedMethodName + "(new " + nested_type_name + "()); }\n";
+    } else {
+      obj = "(new " + nested_type_name + "())";
+    }
+    code += "  public " + nested_type_name + lang_.optional_suffix + " ";
+    code += getNestedMethodName + "(";
+    if (lang_.language != IDLOptions::kCSharp)
+      code += nested_type_name + " obj";
+    code += ") { int o = " + lang_.accessor_prefix + "__offset(";
+    code += NumToString(field.value.offset) +"); ";
+    code += "return o != 0 ? " + conditional_cast + obj + ".__assign(";
+    code += lang_.accessor_prefix;
+    code += "__indirect(" + lang_.accessor_prefix + "__vector(o)), ";
+    code += lang_.accessor_prefix + "bb) : null; }\n";
   }
-    // generate mutators for scalar fields or vectors of scalars
+    // Generate mutators for scalar fields or vectors of scalars.
     if (parser_.opts.mutable_buffer) {
       auto underlying_type = field.value.type.base_type == BASE_TYPE_VECTOR
                     ? field.value.type.VectorType()
                     : field.value.type;
-      // boolean parameters have to be explicitly converted to byte representation
-      auto setter_parameter = underlying_type.base_type == BASE_TYPE_BOOL ? "(byte)(" + field.name + " ? 1 : 0)" : field.name;
+      // Boolean parameters have to be explicitly converted to byte
+      // representation.
+      auto setter_parameter = underlying_type.base_type == BASE_TYPE_BOOL
+        ? "(byte)(" + field.name + " ? 1 : 0)"
+        : field.name;
       auto mutator_prefix = MakeCamel("mutate", lang_.first_camel_upper);
-      //a vector mutator also needs the index of the vector element it should mutate
-      auto mutator_params = (field.value.type.base_type == BASE_TYPE_VECTOR ? "(int j, " : "(") +
-                            GenTypeNameDest(underlying_type) + " " +
-                            field.name + ") { ";
+      // A vector mutator also needs the index of the vector element it should
+      // mutate.
+      auto mutator_params = (field.value.type.base_type == BASE_TYPE_VECTOR
+        ? "(int j, "
+        : "(") + GenTypeNameDest(underlying_type) + " " + field.name + ") { ";
       auto setter_index = field.value.type.base_type == BASE_TYPE_VECTOR
-                    ? "__vector(o) + j * " + NumToString(InlineSize(underlying_type))
-                    : (struct_def.fixed ? "bb_pos + " + NumToString(field.value.offset) : "o + bb_pos");
+        ? lang_.accessor_prefix + "__vector(o) + j * " +
+          NumToString(InlineSize(underlying_type))
+        : (struct_def.fixed
+            ? lang_.accessor_prefix + "bb_pos + " +
+              NumToString(field.value.offset)
+            : "o + " + lang_.accessor_prefix + "bb_pos");
       if (IsScalar(field.value.type.base_type) ||
           (field.value.type.base_type == BASE_TYPE_VECTOR &&
           IsScalar(field.value.type.VectorType().base_type))) {
@@ -951,14 +1135,17 @@
           code += GenSetter(underlying_type) + "(" + setter_index + ", ";
           code += src_cast + setter_parameter + "); }\n";
         } else {
-          code += "int o = __offset(" + NumToString(field.value.offset) + ");";
+          code += "int o = " + lang_.accessor_prefix + "__offset(";
+          code += NumToString(field.value.offset) + ");";
           code += " if (o != 0) { " + GenSetter(underlying_type);
-          code += "(" + setter_index + ", " + src_cast + setter_parameter + "); return true; } else { return false; } }\n";
+          code += "(" + setter_index + ", " + src_cast + setter_parameter +
+                  "); return true; } else { return false; } }\n";
         }
       }
     }
   }
   code += "\n";
+  flatbuffers::FieldDef *key_field = nullptr;
   if (struct_def.fixed) {
     // create a struct constructor function
     code += "  public static " + GenOffsetType(struct_def) + " ";
@@ -968,7 +1155,8 @@
     code += ") {\n";
     GenStructBody(struct_def, code_ptr, "");
     code += "    return ";
-    code += GenOffsetConstruct(struct_def, "builder." + std::string(lang_.get_fbb_offset));
+    code += GenOffsetConstruct(struct_def,
+                               "builder." + std::string(lang_.get_fbb_offset));
     code += ";\n  }\n";
   } else {
     // Generate a method that creates a table in one go. This is only possible
@@ -1047,6 +1235,7 @@
          it != struct_def.fields.vec.end(); ++it) {
       auto &field = **it;
       if (field.deprecated) continue;
+      if (field.key) key_field = &field;
       code += "  public static void " + FunctionStart('A') + "dd";
       code += MakeCamel(field.name);
       code += "(FlatBufferBuilder builder, ";
@@ -1058,10 +1247,15 @@
       code += NumToString(it - struct_def.fields.vec.begin()) + ", ";
       code += SourceCastBasic(field.value.type);
       code += argname;
-      if(!IsScalar(field.value.type.base_type) && field.value.type.base_type != BASE_TYPE_UNION && lang_.language == IDLOptions::kCSharp) {
+      if (!IsScalar(field.value.type.base_type) &&
+          field.value.type.base_type != BASE_TYPE_UNION &&
+          lang_.language == IDLOptions::kCSharp) {
         code += ".Value";
       }
-      code += ", " + GenDefaultValue(field.value, false);
+      code += ", ";
+      if (lang_.language == IDLOptions::kJava)
+        code += SourceCastBasic( field.value.type );
+      code += GenDefaultValue(field.value, false);
       code += "); }\n";
       if (field.value.type.base_type == BASE_TYPE_VECTOR) {
         auto vector_type = field.value.type.VectorType();
@@ -1069,7 +1263,8 @@
         auto elem_size = InlineSize(vector_type);
         if (!IsStruct(vector_type)) {
           // Generate a method to create a vector from a Java array.
-          code += "  public static " + GenVectorOffsetType() + " " + FunctionStart('C') + "reate";
+          code += "  public static " + GenVectorOffsetType() + " ";
+          code += FunctionStart('C') + "reate";
           code += MakeCamel(field.name);
           code += "Vector(FlatBufferBuilder builder, ";
           code += GenTypeBasic(vector_type) + "[] data) ";
@@ -1085,7 +1280,8 @@
           code += SourceCastBasic(vector_type, false);
           code += "data[i]";
           if (lang_.language == IDLOptions::kCSharp &&
-            (vector_type.base_type == BASE_TYPE_STRUCT || vector_type.base_type == BASE_TYPE_STRING))
+              (vector_type.base_type == BASE_TYPE_STRUCT ||
+               vector_type.base_type == BASE_TYPE_STRING))
             code += ".Value";
           code += "); return ";
           code += "builder." + FunctionStart('E') + "ndVector(); }\n";
@@ -1118,7 +1314,8 @@
     if (parser_.root_struct_def_ == &struct_def) {
       code += "  public static void ";
       code += FunctionStart('F') + "inish" + struct_def.name;
-      code += "Buffer(FlatBufferBuilder builder, " + GenOffsetType(struct_def) + " offset) {";
+      code += "Buffer(FlatBufferBuilder builder, " + GenOffsetType(struct_def);
+      code += " offset) {";
       code += " builder." + FunctionStart('F') + "inish(offset";
       if (lang_.language == IDLOptions::kCSharp) {
         code += ".Value";
@@ -1129,12 +1326,66 @@
       code += "); }\n";
     }
   }
+  if (struct_def.has_key) {
+    if (lang_.language == IDLOptions::kJava) {
+      code += "\n  @Override\n  protected int keysCompare(";
+      code += "Integer o1, Integer o2, ByteBuffer _bb) {";
+      code += GenKeyGetter(key_field);
+      code += " }\n";
+    }
+    else {
+      code += "\n  public static VectorOffset ";
+      code += "CreateMySortedVectorOfTables(FlatBufferBuilder builder, ";
+      code += "Offset<" + struct_def.name + ">";
+      code += "[] offsets) {\n";
+      code += "    Array.Sort(offsets, (Offset<" + struct_def.name +
+        "> o1, Offset<" + struct_def.name + "> o2) => " + GenKeyGetter(key_field);
+      code += ");\n";
+      code += "    return builder.CreateVectorOfTables(offsets);\n  }\n";
+    }
+
+    code += "\n  public static " + struct_def.name + lang_.optional_suffix;
+    code += " " + FunctionStart('L') + "ookupByKey(" + GenVectorOffsetType();
+    code += " vectorOffset, " + GenTypeGet(key_field->value.type);
+    code += " key, ByteBuffer bb) {\n";
+    if (key_field->value.type.base_type == BASE_TYPE_STRING) {
+      code += "    byte[] byteKey = ";
+      if (lang_.language == IDLOptions::kJava)
+        code += "key.getBytes(Table.UTF8_CHARSET.get());\n";
+      else
+        code += "System.Text.Encoding.UTF8.GetBytes(key);\n";
+    }
+    code += "    int vectorLocation = " + GenByteBufferLength("bb");
+    code += " - vectorOffset";
+    if (lang_.language == IDLOptions::kCSharp) code += ".Value";
+    code += ";\n    int span = ";
+    code += "bb." + FunctionStart('G') + "etInt(vectorLocation);\n";
+    code += "    int start = 0;\n";
+    code += "    vectorLocation += 4;\n";
+    code += "    while (span != 0) {\n";
+    code += "      int middle = span / 2;\n";
+    code += GenLookupKeyGetter(key_field);
+    code += "      if (comp > 0) {\n";
+    code += "        span = middle;\n";
+    code += "      } else if (comp < 0) {\n";
+    code += "        middle++;\n";
+    code += "        start += middle;\n";
+    code += "        span -= middle;\n";
+    code += "      } else {\n";
+    code += "        return new " + struct_def.name;
+    code += "().__assign(tableOffset, bb);\n";
+    code += "      }\n    }\n";
+    code += "    return null;\n";
+    code += "  }\n";
+  }
   code += "}";
   // Java does not need the closing semi-colon on class definitions.
   code += (lang_.language != IDLOptions::kJava) ? ";" : "";
   code += "\n\n";
-}  
+}
     const LanguageParameters & lang_;
+    // This tracks the current namespace used to determine if a type need to be prefixed by its namespace
+    const Namespace *cur_name_space_;
 };
 }  // namespace general
 
@@ -1156,8 +1407,7 @@
     auto &enum_def = **it;
     if (make_rule != "") make_rule += " ";
     std::string directory =
-        BaseGenerator::NamespaceDir(parser, path, *enum_def.defined_namespace) +
-        kPathSeparator;
+        BaseGenerator::NamespaceDir(parser, path, *enum_def.defined_namespace);
     make_rule += directory + enum_def.name + lang.file_extension;
   }
 
@@ -1166,8 +1416,8 @@
     auto &struct_def = **it;
     if (make_rule != "") make_rule += " ";
     std::string directory =
-        BaseGenerator::NamespaceDir(parser, path, *struct_def.defined_namespace) +
-        kPathSeparator;
+        BaseGenerator::NamespaceDir(parser, path,
+                                    *struct_def.defined_namespace);
     make_rule += directory + struct_def.name + lang.file_extension;
   }
 
diff --git a/src/idl_gen_go.cpp b/src/idl_gen_go.cpp
index a04b6ba..dadb350 100644
--- a/src/idl_gen_go.cpp
+++ b/src/idl_gen_go.cpp
@@ -85,7 +85,33 @@
 // End enum code.
 static void EndEnum(std::string *code_ptr) {
   std::string &code = *code_ptr;
-  code += ")\n";
+  code += ")\n\n";
+}
+
+// Begin enum name code.
+static void BeginEnumNames(const EnumDef &enum_def, std::string *code_ptr) {
+  std::string &code = *code_ptr;
+  code += "var EnumNames";
+  code += enum_def.name;
+  code += " = map[int]string{\n";
+}
+
+// A single enum name member.
+static void EnumNameMember(const EnumDef &enum_def, const EnumVal ev,
+                           std::string *code_ptr) {
+  std::string &code = *code_ptr;
+  code += "\t";
+  code += enum_def.name;
+  code += ev.name;
+  code += ":\"";
+  code += ev.name;
+  code += "\",\n";
+}
+
+// End enum name code.
+static void EndEnumNames(std::string *code_ptr) {
+  std::string &code = *code_ptr;
+  code += "}\n\n";
 }
 
 // Initialize a new struct or table from existing data.
@@ -100,7 +126,7 @@
   code += " {\n";
   code += "\tn := flatbuffers.GetUOffsetT(buf[offset:])\n";
   code += "\tx := &" + struct_def.name + "{}\n";
-  code += "\tx.Init(buf, n + offset)\n";
+  code += "\tx.Init(buf, n+offset)\n";
   code += "\treturn x\n";
   code += "}\n\n";
 }
@@ -118,6 +144,23 @@
   code += "}\n\n";
 }
 
+// Implement the table accessor
+static void GenTableAccessor(const StructDef &struct_def,
+                               std::string *code_ptr) {
+  std::string &code = *code_ptr;
+
+  GenReceiver(struct_def, code_ptr);
+  code += " Table() flatbuffers.Table ";
+  code += "{\n";
+
+  if (struct_def.fixed) {
+      code += "\treturn rcv._tab.Table\n";
+  } else {
+      code += "\treturn rcv._tab\n";
+  }
+  code += "}\n\n";
+}
+
 // Get the length of a vector.
 static void GetVectorLen(const StructDef &struct_def,
                          const FieldDef &field,
@@ -152,9 +195,10 @@
   std::string getter = GenGetter(field.value.type);
   GenReceiver(struct_def, code_ptr);
   code += " " + MakeCamel(field.name);
-  code += "() " + TypeName(field) + " { return " + getter;
+  code += "() " + TypeName(field) + " {\n";
+  code +="\treturn " + getter;
   code += "(rcv._tab.Pos + flatbuffers.UOffsetT(";
-  code += NumToString(field.value.offset) + ")) }\n";
+  code += NumToString(field.value.offset) + "))\n}\n";
 }
 
 // Get the value of a table's scalar.
@@ -186,7 +230,7 @@
   code += "\tif obj == nil {\n";
   code += "\t\tobj = new(" + TypeName(field) + ")\n";
   code += "\t}\n";
-  code += "\tobj.Init(rcv._tab.Bytes, rcv._tab.Pos + ";
+  code += "\tobj.Init(rcv._tab.Bytes, rcv._tab.Pos+";
   code += NumToString(field.value.offset) + ")";
   code += "\n\treturn obj\n";
   code += "}\n";
@@ -261,9 +305,6 @@
   if (!(vectortype.struct_def->fixed)) {
     code += "\t\tx = rcv._tab.Indirect(x)\n";
   }
-  code += "\tif obj == nil {\n";
-  code += "\t\tobj = new(" + TypeName(field) + ")\n";
-  code += "\t}\n";
   code += "\t\tobj.Init(rcv._tab.Bytes, x)\n";
   code += "\t\treturn true\n\t}\n";
   code += "\treturn false\n";
@@ -284,7 +325,7 @@
   code += OffsetPrefix(field);
   code += "\t\ta := rcv._tab.Vector(o)\n";
   code += "\t\treturn " + GenGetter(field.value.type) + "(";
-  code += "a + flatbuffers.UOffsetT(j * ";
+  code += "a + flatbuffers.UOffsetT(j*";
   code += NumToString(InlineSize(vectortype)) + "))\n";
   code += "\t}\n";
   if (vectortype.base_type == BASE_TYPE_STRING) {
@@ -300,7 +341,10 @@
                              std::string *code_ptr) {
   std::string &code = *code_ptr;
 
-  code += "\n";
+  if (code.substr(code.length() - 2) != "\n\n") {
+      // a previous mutate has not put an extra new line
+      code += "\n";
+  }
   code += "func Create" + struct_def.name;
   code += "(builder *flatbuffers.Builder";
 }
@@ -342,20 +386,20 @@
                               const char *nameprefix,
                               std::string *code_ptr) {
   std::string &code = *code_ptr;
-  code += "    builder.Prep(" + NumToString(struct_def.minalign) + ", ";
+  code += "\tbuilder.Prep(" + NumToString(struct_def.minalign) + ", ";
   code += NumToString(struct_def.bytesize) + ")\n";
   for (auto it = struct_def.fields.vec.rbegin();
        it != struct_def.fields.vec.rend();
        ++it) {
     auto &field = **it;
     if (field.padding)
-      code += "    builder.Pad(" + NumToString(field.padding) + ")\n";
+      code += "\tbuilder.Pad(" + NumToString(field.padding) + ")\n";
     if (IsStruct(field.value.type)) {
       StructBuilderBody(*field.value.type.struct_def,
                         (nameprefix + (field.name + "_")).c_str(),
                         code_ptr);
     } else {
-      code += "    builder.Prepend" + GenMethod(field) + "(";
+      code += "\tbuilder.Prepend" + GenMethod(field) + "(";
       code += nameprefix + MakeCamel(field.name, false) + ")\n";
     }
   }
@@ -363,7 +407,7 @@
 
 static void EndBuilderBody(std::string *code_ptr) {
   std::string &code = *code_ptr;
-  code += "    return builder.Offset()\n";
+  code += "\treturn builder.Offset()\n";
   code += "}\n";
 }
 
@@ -372,10 +416,10 @@
                             std::string *code_ptr) {
   std::string &code = *code_ptr;
   code += "func " + struct_def.name + "Start";
-  code += "(builder *flatbuffers.Builder) { ";
-  code += "builder.StartObject(";
+  code += "(builder *flatbuffers.Builder) {\n";
+  code += "\tbuilder.StartObject(";
   code += NumToString(struct_def.fields.vec.size());
-  code += ") }\n";
+  code += ")\n}\n";
 }
 
 // Set the value of a table's field.
@@ -392,8 +436,8 @@
   } else {
     code += GenTypeBasic(field.value.type);
   }
-  code += ") ";
-  code += "{ builder.Prepend";
+  code += ") {\n";
+  code += "\tbuilder.Prepend";
   code += GenMethod(field) + "Slot(";
   code += NumToString(offset) + ", ";
   if (!IsScalar(field.value.type.base_type) && (!struct_def.fixed)) {
@@ -404,7 +448,7 @@
     code += MakeCamel(field.name, false);
   }
   code += ", " + field.value.constant;
-  code += ") }\n";
+  code += ")\n}\n";
 }
 
 // Set the value of one of the members of a table's vector.
@@ -415,7 +459,7 @@
   code += "func " + struct_def.name + "Start";
   code += MakeCamel(field.name);
   code += "Vector(builder *flatbuffers.Builder, numElems int) ";
-  code += "flatbuffers.UOffsetT { return builder.StartVector(";
+  code += "flatbuffers.UOffsetT {\n\treturn builder.StartVector(";
   auto vector_type = field.value.type.VectorType();
   auto alignment = InlineAlignment(vector_type);
   auto elem_size = InlineSize(vector_type);
@@ -430,7 +474,7 @@
   std::string &code = *code_ptr;
   code += "func " + struct_def.name + "End";
   code += "(builder *flatbuffers.Builder) flatbuffers.UOffsetT ";
-  code += "{ return builder.EndObject() }\n";
+  code += "{\n\treturn builder.EndObject()\n}\n";
 }
 
 // Generate the receiver for function signatures.
@@ -439,7 +483,7 @@
   code += "func (rcv *" + struct_def.name + ")";
 }
 
-// Generate a struct field, conditioned on its child type(s).
+// Generate a struct field getter, conditioned on its child type(s).
 static void GenStructAccessor(const StructDef &struct_def,
                               const FieldDef &field,
                               std::string *code_ptr) {
@@ -486,6 +530,48 @@
   }
 }
 
+// Mutate the value of a struct's scalar.
+static void MutateScalarFieldOfStruct(const StructDef &struct_def,
+                                   const FieldDef &field,
+                                   std::string *code_ptr) {
+  std::string &code = *code_ptr;
+  std::string type = MakeCamel(GenTypeBasic(field.value.type));
+  std::string setter = "rcv._tab.Mutate" + type;
+  GenReceiver(struct_def, code_ptr);
+  code += " Mutate" + MakeCamel(field.name);
+  code += "(n " + TypeName(field) + ") bool {\n\treturn " + setter;
+  code += "(rcv._tab.Pos+flatbuffers.UOffsetT(";
+  code += NumToString(field.value.offset) + "), n)\n}\n\n";
+}
+
+// Mutate the value of a table's scalar.
+static void MutateScalarFieldOfTable(const StructDef &struct_def,
+                                  const FieldDef &field,
+                                  std::string *code_ptr) {
+  std::string &code = *code_ptr;
+  std::string type = MakeCamel(GenTypeBasic(field.value.type));
+  std::string setter = "rcv._tab.Mutate" + type + "Slot";
+  GenReceiver(struct_def, code_ptr);
+  code += " Mutate" + MakeCamel(field.name);
+  code += "(n " + TypeName(field) + ") bool {\n\treturn ";
+  code += setter + "(" + NumToString(field.value.offset) + ", n)\n";
+  code += "}\n\n";
+}
+
+// Generate a struct field setter, conditioned on its child type(s).
+static void GenStructMutator(const StructDef &struct_def,
+                              const FieldDef &field,
+                              std::string *code_ptr) {
+  GenComment(field.doc_comment, code_ptr, nullptr, "");
+  if (IsScalar(field.value.type.base_type)) {
+    if (struct_def.fixed) {
+      MutateScalarFieldOfStruct(struct_def, field, code_ptr);
+    } else {
+      MutateScalarFieldOfTable(struct_def, field, code_ptr);
+    }
+  }
+}
+
 // Generate table constructors, conditioned on its members' types.
 static void GenTableBuilders(const StructDef &struct_def,
                              std::string *code_ptr) {
@@ -509,13 +595,12 @@
 
 // Generate struct or table methods.
 static void GenStruct(const StructDef &struct_def,
-                      std::string *code_ptr,
-                      StructDef *root_struct_def) {
+                      std::string *code_ptr) {
   if (struct_def.generated) return;
 
   GenComment(struct_def.doc_comment, code_ptr, nullptr);
   BeginClass(struct_def, code_ptr);
-  if (&struct_def == root_struct_def) {
+  if (!struct_def.fixed) {
     // Generate a special accessor for the table that has been declared as
     // the root type.
     NewRootTypeFromBuffer(struct_def, code_ptr);
@@ -523,6 +608,10 @@
   // Generate the Init method that sets the field in a pre-existing
   // accessor object. This is to allow object reuse.
   InitializeExisting(struct_def, code_ptr);
+  // Generate _tab accessor
+  GenTableAccessor(struct_def, code_ptr);
+
+  // Generate struct fields accessors
   for (auto it = struct_def.fields.vec.begin();
        it != struct_def.fields.vec.end();
        ++it) {
@@ -530,8 +619,10 @@
     if (field.deprecated) continue;
 
     GenStructAccessor(struct_def, field, code_ptr);
+    GenStructMutator(struct_def, field, code_ptr);
   }
 
+  // Generate builders
   if (struct_def.fixed) {
     // create a struct constructor function
     GenStructBuilder(struct_def, code_ptr);
@@ -555,6 +646,15 @@
     EnumMember(enum_def, ev, code_ptr);
   }
   EndEnum(code_ptr);
+
+  BeginEnumNames(enum_def, code_ptr);
+  for (auto it = enum_def.vals.vec.begin();
+       it != enum_def.vals.vec.end();
+       ++it) {
+    auto &ev = **it;
+    EnumNameMember(enum_def, ev, code_ptr);
+  }
+  EndEnumNames(code_ptr);
 }
 
 // Returns the function name that is able to read a value of the given type.
@@ -638,7 +738,7 @@
     for (auto it = parser_.structs_.vec.begin();
          it != parser_.structs_.vec.end(); ++it) {
       std::string declcode;
-      go::GenStruct(**it, &declcode, parser_.root_struct_def_);
+      go::GenStruct(**it, &declcode);
       if (!SaveType(**it, declcode, true)) return false;
     }
 
@@ -655,7 +755,7 @@
     if (needs_imports) {
       code += "import (\n";
       code += "\tflatbuffers \"github.com/google/flatbuffers/go\"\n";
-      code += ")\n";
+      code += ")\n\n";
     }
   }
 
@@ -681,4 +781,3 @@
 }
 
 }  // namespace flatbuffers
-
diff --git a/src/idl_gen_grpc.cpp b/src/idl_gen_grpc.cpp
index 2bf0e91..a540b8b 100644
--- a/src/idl_gen_grpc.cpp
+++ b/src/idl_gen_grpc.cpp
@@ -19,12 +19,14 @@
 #include "flatbuffers/flatbuffers.h"
 #include "flatbuffers/idl.h"
 #include "flatbuffers/util.h"
+#include "flatbuffers/code_generators.h"
 
 #include "src/compiler/cpp_generator.h"
+#include "src/compiler/go_generator.h"
 
 namespace flatbuffers {
 
-class FlatBufMethod : public grpc_cpp_generator::Method {
+class FlatBufMethod : public grpc_generator::Method {
  public:
   enum Streaming { kNone, kClient, kServer, kBiDi };
 
@@ -52,6 +54,14 @@
     return GRPCType(*method_->response);
   }
 
+  std::string input_name() const {
+    return (*method_->request).name;
+  }
+
+  std::string output_name() const {
+    return (*method_->response).name;
+  }
+
   bool NoStreaming() const { return streaming_ == kNone; }
   bool ClientOnlyStreaming() const { return streaming_ == kClient; }
   bool ServerOnlyStreaming() const { return streaming_ == kServer; }
@@ -62,7 +72,7 @@
   Streaming streaming_;
 };
 
-class FlatBufService : public grpc_cpp_generator::Service {
+class FlatBufService : public grpc_generator::Service {
  public:
   FlatBufService(const ServiceDef *service) : service_(service) {}
 
@@ -72,8 +82,8 @@
     return static_cast<int>(service_->calls.vec.size());
   };
 
-  std::unique_ptr<const grpc_cpp_generator::Method> method(int i) const {
-    return std::unique_ptr<const grpc_cpp_generator::Method>(
+  std::unique_ptr<const grpc_generator::Method> method(int i) const {
+    return std::unique_ptr<const grpc_generator::Method>(
           new FlatBufMethod(service_->calls.vec[i]));
   };
 
@@ -81,7 +91,7 @@
   const ServiceDef *service_;
 };
 
-class FlatBufPrinter : public grpc_cpp_generator::Printer {
+class FlatBufPrinter : public grpc_generator::Printer {
  public:
   FlatBufPrinter(std::string *str)
     : str_(str), escape_char_('$'), indent_(0) {}
@@ -133,10 +143,11 @@
   int indent_;
 };
 
-class FlatBufFile : public grpc_cpp_generator::File {
+class FlatBufFile : public grpc_generator::File {
  public:
   FlatBufFile(const Parser &parser, const std::string &file_name)
     : parser_(parser), file_name_(file_name) {}
+  FlatBufFile &operator=(const FlatBufFile &);
 
   std::string filename() const { return file_name_; }
   std::string filename_without_ext() const {
@@ -158,17 +169,21 @@
     return "#include \"flatbuffers/grpc.h\"\n";
   }
 
+  std::string additional_imports() const {
+    return "import \"github.com/google/flatbuffers/go\"";
+  }
+
   int service_count() const {
     return static_cast<int>(parser_.services_.vec.size());
   };
 
-  std::unique_ptr<const grpc_cpp_generator::Service> service(int i) const {
-    return std::unique_ptr<const grpc_cpp_generator::Service> (
+  std::unique_ptr<const grpc_generator::Service> service(int i) const {
+    return std::unique_ptr<const grpc_generator::Service> (
           new FlatBufService(parser_.services_.vec[i]));
   }
 
-  std::unique_ptr<grpc_cpp_generator::Printer> CreatePrinter(std::string *str) const {
-    return std::unique_ptr<grpc_cpp_generator::Printer>(
+  std::unique_ptr<grpc_generator::Printer> CreatePrinter(std::string *str) const {
+    return std::unique_ptr<grpc_generator::Printer>(
           new FlatBufPrinter(str));
   }
 
@@ -177,7 +192,47 @@
   const std::string &file_name_;
 };
 
-bool GenerateGRPC(const Parser &parser,
+class GoGRPCGenerator : public flatbuffers::BaseGenerator {
+ public:
+  GoGRPCGenerator(const Parser &parser, const std::string &path,
+                  const std::string &file_name)
+    : BaseGenerator(parser, path, file_name, "", "" /*Unused*/),
+      parser_(parser), path_(path), file_name_(file_name) {}
+
+  bool generate() {
+    FlatBufFile file(parser_, file_name_);
+    grpc_go_generator::Parameters p;
+    p.custom_method_io_type = "flatbuffers.Builder";
+    for (int i = 0; i < file.service_count(); i++) {
+      auto service = file.service(i);
+      const Definition *def = parser_.services_.vec[i];
+      p.package_name = LastNamespacePart(*(def->defined_namespace));
+      std::string output = grpc_go_generator::GenerateServiceSource(&file, service.get(), &p);
+      std::string filename = NamespaceDir(*def->defined_namespace) + def->name + "_grpc.go";
+      if (!flatbuffers::SaveFile(filename.c_str(), output, false))
+        return false;
+    }
+    return true;
+  }
+
+ protected:
+  const Parser &parser_;
+  const std::string &path_, &file_name_;
+};
+
+bool GenerateGoGRPC(const Parser &parser,
+                    const std::string &path,
+                    const std::string &file_name) {
+  int nservices = 0;
+  for (auto it = parser.services_.vec.begin();
+       it != parser.services_.vec.end(); ++it) {
+    if (!(*it)->generated) nservices++;
+  }
+  if (!nservices) return true;
+  return GoGRPCGenerator(parser, path, file_name).generate();
+}
+
+bool GenerateCppGRPC(const Parser &parser,
                   const std::string &/*path*/,
                   const std::string &file_name) {
 
diff --git a/src/idl_gen_js.cpp b/src/idl_gen_js.cpp
index 32a06f1..32c660c 100644
--- a/src/idl_gen_js.cpp
+++ b/src/idl_gen_js.cpp
@@ -79,7 +79,7 @@
     for (auto it = parser_.structs_.vec.begin();
          it != parser_.structs_.vec.end(); ++it) {
       auto &struct_def = **it;
-      GenStruct(struct_def, decl_code_ptr, exports_code_ptr);
+      GenStruct(parser_, struct_def, decl_code_ptr, exports_code_ptr);
     }
   }
   void GenNamespaces(std::string *code_ptr, std::string *exports_ptr) {
@@ -110,7 +110,7 @@
   std::string &exports = *exports_ptr;
   for (auto it = sorted_namespaces.begin();
        it != sorted_namespaces.end(); it++) {
-    code += "/**\n * @const\n*/\n";
+    code += "/**\n * @const\n * @namespace\n */\n";
     if (it->find('.') == std::string::npos) {
       code += "var ";
       exports += "this." + *it + " = " + *it + ";\n";
@@ -361,7 +361,7 @@
 }
 
 // Generate an accessor struct with constructor for a flatbuffers struct.
-void GenStruct(StructDef &struct_def, std::string *code_ptr, std::string *exports_ptr) {
+void GenStruct(const Parser &parser, StructDef &struct_def, std::string *code_ptr, std::string *exports_ptr) {
   if (struct_def.generated) return;
   std::string &code = *code_ptr;
   std::string &exports = *exports_ptr;
@@ -550,6 +550,22 @@
     }
     code += "};\n\n";
 
+    // Adds the mutable scalar value to the output
+    if (IsScalar(field.value.type.base_type) && parser.opts.mutable_buffer) {
+      std::string annotations = "@param {" + GenTypeName(field.value.type, true) + "} value\n";
+      GenDocComment(code_ptr, annotations +
+        "@returns {boolean}");
+
+      code += object_name + ".prototype.mutate_" + field.name + " = function(value) {\n";
+      code += "  var offset = this.bb.__offset(this.bb_pos, " + NumToString(field.value.offset) + ");\n\n";
+      code += "  if (offset === 0) {\n";
+      code += "    return false;\n";
+      code += "  }\n\n";
+      code += "  this.bb.write" + MakeCamel(GenType(field.value.type)) + "(this.bb_pos + offset, value);\n";
+      code += "  return true;\n";
+      code += "};\n\n";
+    }
+
     // Emit vector helpers
     if (field.value.type.base_type == BASE_TYPE_VECTOR) {
       // Emit a length helper
@@ -565,7 +581,7 @@
         code += object_name + ".prototype." + MakeCamel(field.name, false);
         code += "Array = function() {\n" + offset_prefix;
         code += "new " + GenType(vectorType) + "Array(this.bb.bytes().buffer, "
-          "this.bb.__vector(this.bb_pos + offset), "
+          "this.bb.bytes().byteOffset + this.bb.__vector(this.bb_pos + offset), "
           "this.bb.__vector_len(this.bb_pos + offset)) : null;\n};\n\n";
       }
     }
diff --git a/src/idl_gen_php.cpp b/src/idl_gen_php.cpp
index af3b06d..a893f98 100644
--- a/src/idl_gen_php.cpp
+++ b/src/idl_gen_php.cpp
@@ -89,10 +89,10 @@
         code += classcode;
 
         std::string filename = NamespaceDir(*def.defined_namespace) +
-                               kPathSeparator + def.name + ".php";
+                               def.name + ".php";
         return SaveFile(filename.c_str(), code, false);
       }
-      
+
     // Begin a class declaration.
     static void BeginClass(const StructDef &struct_def, std::string *code_ptr) {
       std::string &code = *code_ptr;
@@ -955,7 +955,7 @@
       code += Indent + Indent + "return $builder->offset();\n";
       code += Indent + "}\n";
     }
-      
+
     };
     }  // namespace php
 
diff --git a/src/idl_gen_python.cpp b/src/idl_gen_python.cpp
index 7e8dc0e..76fea3e 100644
--- a/src/idl_gen_python.cpp
+++ b/src/idl_gen_python.cpp
@@ -94,7 +94,7 @@
   code += Indent + Indent + "x = " + struct_def.name + "()\n";
   code += Indent + Indent + "x.Init(buf, n + offset)\n";
   code += Indent + Indent + "return x\n";
-  code += "\n\n";
+  code += "\n";
 }
 
 // Initialize an existing object with other data, to avoid an allocation.
@@ -478,13 +478,12 @@
 
 // Generate struct or table methods.
 static void GenStruct(const StructDef &struct_def,
-                      std::string *code_ptr,
-                      StructDef *root_struct_def) {
+                      std::string *code_ptr) {
   if (struct_def.generated) return;
 
   GenComment(struct_def.doc_comment, code_ptr, nullptr, "# ");
   BeginClass(struct_def, code_ptr);
-  if (&struct_def == root_struct_def) {
+  if (!struct_def.fixed) {
     // Generate a special accessor for the table that has been declared as
     // the root type.
     NewRootTypeFromBuffer(struct_def, code_ptr);
@@ -621,7 +620,7 @@
          it != parser_.structs_.vec.end(); ++it) {
       auto &struct_def = **it;
       std::string declcode;
-      GenStruct(struct_def, &declcode, parser_.root_struct_def_);
+      GenStruct(struct_def, &declcode);
       if (!SaveType(struct_def, declcode, true)) return false;
     }
     return true;
@@ -656,7 +655,7 @@
     BeginFile(LastNamespacePart(*def.defined_namespace), needs_imports, &code);
     code += classcode;
     std::string filename = NamespaceDir(*def.defined_namespace) +
-                           kPathSeparator + def.name + ".py";
+                           def.name + ".py";
     return SaveFile(filename.c_str(), code, false);
   }
 };
diff --git a/src/idl_gen_text.cpp b/src/idl_gen_text.cpp
index dd96912..17cd987 100644
--- a/src/idl_gen_text.cpp
+++ b/src/idl_gen_text.cpp
@@ -22,7 +22,7 @@
 
 namespace flatbuffers {
 
-static void GenStruct(const StructDef &struct_def, const Table *table,
+static bool GenStruct(const StructDef &struct_def, const Table *table,
                       int indent, const IDLOptions &opts,
                       std::string *_text);
 
@@ -48,7 +48,7 @@
 // Print (and its template specialization below for pointers) generate text
 // for a single FlatBuffer value into JSON format.
 // The general case for scalars:
-template<typename T> void Print(T val, Type type, int /*indent*/,
+template<typename T> bool Print(T val, Type type, int /*indent*/,
                                 StructDef * /*union_sd*/,
                                 const IDLOptions &opts,
                                 std::string *_text) {
@@ -57,7 +57,7 @@
     auto enum_val = type.enum_def->ReverseLookup(static_cast<int>(val));
     if (enum_val) {
       OutputIdentifier(enum_val->name, opts, _text);
-      return;
+      return true;
     }
   }
 
@@ -66,10 +66,12 @@
   } else {
     text += NumToString(val);
   }
+
+  return true;
 }
 
 // Print a vector a sequence of JSON values, comma separated, wrapped in "[]".
-template<typename T> void PrintVector(const Vector<T> &v, Type type,
+template<typename T> bool PrintVector(const Vector<T> &v, Type type,
                                       int indent, const IDLOptions &opts,
                                       std::string *_text) {
   std::string &text = *_text;
@@ -81,19 +83,25 @@
       text += NewLine(opts);
     }
     text.append(indent + Indent(opts), ' ');
-    if (IsStruct(type))
-      Print(v.GetStructFromOffset(i * type.struct_def->bytesize), type,
-            indent + Indent(opts), nullptr, opts, _text);
-    else
-      Print(v[i], type, indent + Indent(opts), nullptr,
-            opts, _text);
+    if (IsStruct(type)) {
+      if (!Print(v.GetStructFromOffset(i * type.struct_def->bytesize), type,
+                 indent + Indent(opts), nullptr, opts, _text)) {
+        return false;
+      }
+    } else {
+      if (!Print(v[i], type, indent + Indent(opts), nullptr,
+                 opts, _text)) {
+        return false;
+      }
+    }
   }
   text += NewLine(opts);
   text.append(indent, ' ');
   text += "]";
+  return true;
 }
 
-static void EscapeString(const String &s, std::string *_text) {
+static bool EscapeString(const String &s, std::string *_text, const IDLOptions& opts) {
   std::string &text = *_text;
   text += "\"";
   for (uoffset_t i = 0; i < s.size(); i++) {
@@ -113,27 +121,53 @@
           // Not printable ASCII data. Let's see if it's valid UTF-8 first:
           const char *utf8 = s.c_str() + i;
           int ucc = FromUTF8(&utf8);
-          if (ucc >= 0x80 && ucc <= 0xFFFF) {
-            // Parses as Unicode within JSON's \uXXXX range, so use that.
-            text += "\\u";
-            text += IntToStringHex(ucc, 4);
+          if (ucc < 0) {
+            if (opts.allow_non_utf8) {
+              text += "\\x";
+              text += IntToStringHex(static_cast<uint8_t>(c), 2);
+            } else {
+              // There are two cases here:
+              //
+              // 1) We reached here by parsing an IDL file. In that case,
+              // we previously checked for non-UTF-8, so we shouldn't reach
+              // here.
+              //
+              // 2) We reached here by someone calling GenerateText()
+              // on a previously-serialized flatbuffer. The data might have
+              // non-UTF-8 Strings, or might be corrupt.
+              //
+              // In both cases, we have to give up and inform the caller
+              // they have no JSON.
+              return false;
+            }
+          } else {
+            if (ucc <= 0xFFFF) {
+              // Parses as Unicode within JSON's \uXXXX range, so use that.
+              text += "\\u";
+              text += IntToStringHex(ucc, 4);
+            } else if (ucc <= 0x10FFFF) {
+              // Encode Unicode SMP values to a surrogate pair using two \u escapes.
+              uint32_t base = ucc - 0x10000;
+              auto high_surrogate = (base >> 10) + 0xD800;
+              auto low_surrogate = (base & 0x03FF) + 0xDC00;
+              text += "\\u";
+              text += IntToStringHex(high_surrogate, 4);
+              text += "\\u";
+              text += IntToStringHex(low_surrogate, 4);
+            }
             // Skip past characters recognized.
             i = static_cast<uoffset_t>(utf8 - s.c_str() - 1);
-          } else {
-            // It's either unprintable ASCII, arbitrary binary, or Unicode data
-            // that doesn't fit \uXXXX, so use \xXX escape code instead.
-            text += "\\x";
-            text += IntToStringHex(static_cast<uint8_t>(c), 2);
           }
         }
         break;
     }
   }
   text += "\"";
+  return true;
 }
 
 // Specialization of Print above for pointer types.
-template<> void Print<const void *>(const void *val,
+template<> bool Print<const void *>(const void *val,
                                     Type type, int indent,
                                     StructDef *union_sd,
                                     const IDLOptions &opts,
@@ -143,21 +177,27 @@
       // If this assert hits, you have an corrupt buffer, a union type field
       // was not present or was out of range.
       assert(union_sd);
-      GenStruct(*union_sd,
-                reinterpret_cast<const Table *>(val),
-                indent,
-                opts,
-                _text);
+      if (!GenStruct(*union_sd,
+                     reinterpret_cast<const Table *>(val),
+                     indent,
+                     opts,
+                     _text)) {
+        return false;
+      }
       break;
     case BASE_TYPE_STRUCT:
-      GenStruct(*type.struct_def,
-                reinterpret_cast<const Table *>(val),
-                indent,
-                opts,
-                _text);
+      if (!GenStruct(*type.struct_def,
+                     reinterpret_cast<const Table *>(val),
+                     indent,
+                     opts,
+                     _text)) {
+        return false;
+      }
       break;
     case BASE_TYPE_STRING: {
-      EscapeString(*reinterpret_cast<const String *>(val), _text);
+      if (!EscapeString(*reinterpret_cast<const String *>(val), _text, opts)) {
+        return false;
+      }
       break;
     }
     case BASE_TYPE_VECTOR:
@@ -167,31 +207,35 @@
         #define FLATBUFFERS_TD(ENUM, IDLTYPE, CTYPE, JTYPE, GTYPE, NTYPE, \
           PTYPE) \
           case BASE_TYPE_ ## ENUM: \
-            PrintVector<CTYPE>( \
-              *reinterpret_cast<const Vector<CTYPE> *>(val), \
-              type, indent, opts, _text); break;
+            if (!PrintVector<CTYPE>( \
+                  *reinterpret_cast<const Vector<CTYPE> *>(val), \
+                  type, indent, opts, _text)) { \
+              return false; \
+            } \
+            break;
           FLATBUFFERS_GEN_TYPES(FLATBUFFERS_TD)
         #undef FLATBUFFERS_TD
       }
       break;
     default: assert(0);
   }
+  return true;
 }
 
 // Generate text for a scalar field.
-template<typename T> static void GenField(const FieldDef &fd,
+template<typename T> static bool GenField(const FieldDef &fd,
                                           const Table *table, bool fixed,
                                           const IDLOptions &opts,
                                           int indent,
                                           std::string *_text) {
-  Print(fixed ?
+  return Print(fixed ?
     reinterpret_cast<const Struct *>(table)->GetField<T>(fd.value.offset) :
     table->GetField<T>(fd.value.offset, 0), fd.value.type, indent, nullptr,
                                             opts, _text);
 }
 
 // Generate text for non-scalar field.
-static void GenFieldOffset(const FieldDef &fd, const Table *table, bool fixed,
+static bool GenFieldOffset(const FieldDef &fd, const Table *table, bool fixed,
                            int indent, StructDef *union_sd,
                            const IDLOptions &opts, std::string *_text) {
   const void *val = nullptr;
@@ -205,12 +249,12 @@
       ? table->GetStruct<const void *>(fd.value.offset)
       : table->GetPointer<const void *>(fd.value.offset);
   }
-  Print(val, fd.value.type, indent, union_sd, opts, _text);
+  return Print(val, fd.value.type, indent, union_sd, opts, _text);
 }
 
 // Generate text for a struct or table, values separated by commas, indented,
 // and bracketed by "{}"
-static void GenStruct(const StructDef &struct_def, const Table *table,
+static bool GenStruct(const StructDef &struct_def, const Table *table,
                       int indent, const IDLOptions &opts,
                       std::string *_text) {
   std::string &text = *_text;
@@ -238,8 +282,10 @@
            #define FLATBUFFERS_TD(ENUM, IDLTYPE, CTYPE, JTYPE, GTYPE, NTYPE, \
              PTYPE) \
              case BASE_TYPE_ ## ENUM: \
-                GenField<CTYPE>(fd, table, struct_def.fixed, \
-                                opts, indent + Indent(opts), _text); \
+                if (!GenField<CTYPE>(fd, table, struct_def.fixed, \
+                                     opts, indent + Indent(opts), _text)) { \
+                  return false; \
+                } \
                 break;
             FLATBUFFERS_GEN_TYPES_SCALAR(FLATBUFFERS_TD)
           #undef FLATBUFFERS_TD
@@ -249,8 +295,10 @@
             case BASE_TYPE_ ## ENUM:
             FLATBUFFERS_GEN_TYPES_POINTER(FLATBUFFERS_TD)
           #undef FLATBUFFERS_TD
-              GenFieldOffset(fd, table, struct_def.fixed, indent + Indent(opts),
-                             union_sd, opts, _text);
+              if (!GenFieldOffset(fd, table, struct_def.fixed, indent + Indent(opts),
+                                  union_sd, opts, _text)) {
+                return false;
+              }
               break;
         }
         if (fd.value.type.base_type == BASE_TYPE_UTYPE) {
@@ -269,20 +317,24 @@
   text += NewLine(opts);
   text.append(indent, ' ');
   text += "}";
+  return true;
 }
 
 // Generate a text representation of a flatbuffer in JSON format.
-void GenerateText(const Parser &parser, const void *flatbuffer,
+bool GenerateText(const Parser &parser, const void *flatbuffer,
                   std::string *_text) {
   std::string &text = *_text;
   assert(parser.root_struct_def_);  // call SetRootType()
   text.reserve(1024);   // Reduce amount of inevitable reallocs.
-  GenStruct(*parser.root_struct_def_,
-            GetRoot<Table>(flatbuffer),
-            0,
-            parser.opts,
-            _text);
+  if (!GenStruct(*parser.root_struct_def_,
+                 GetRoot<Table>(flatbuffer),
+                 0,
+                 parser.opts,
+                 _text)) {
+    return false;
+  }
   text += NewLine(parser.opts);
+  return true;
 }
 
 std::string TextFileName(const std::string &path,
@@ -295,7 +347,9 @@
                       const std::string &file_name) {
   if (!parser.builder_.GetSize() || !parser.root_struct_def_) return true;
   std::string text;
-  GenerateText(parser, parser.builder_.GetBufferPointer(), &text);
+  if (!GenerateText(parser, parser.builder_.GetBufferPointer(), &text)) {
+    return false;
+  }
   return flatbuffers::SaveFile(TextFileName(path, file_name).c_str(),
                                text,
                                false);
diff --git a/src/idl_parser.cpp b/src/idl_parser.cpp
index a5f325d..ef6e1f5 100644
--- a/src/idl_parser.cpp
+++ b/src/idl_parser.cpp
@@ -61,6 +61,17 @@
 #define NEXT() ECHECK(Next())
 #define EXPECT(tok) ECHECK(Expect(tok))
 
+static bool ValidateUTF8(const std::string &str) {
+  const char *s = &str[0];
+  const char * const sEnd = s + str.length();
+  while (s < sEnd) {
+    if (FromUTF8(&s) < 0) {
+      return false;
+    }
+  }
+  return true;
+}
+
 CheckedError Parser::Error(const std::string &msg) {
   error_ = file_being_parsed_.length() ? AbsolutePath(file_being_parsed_) : "";
   #ifdef _WIN32
@@ -208,7 +219,7 @@
       return Error("escape code must be followed by " + NumToString(nibbles) +
                    " hex digits");
   std::string target(cursor_, cursor_ + nibbles);
-  *val = StringToUInt(target.c_str(), 16);
+  *val = StringToUInt(target.c_str(), nullptr, 16);
   cursor_ += nibbles;
   return NoError();
 }
@@ -320,6 +331,9 @@
             "illegal Unicode sequence (unpaired high surrogate)");
         }
         cursor_++;
+        if (!opts.allow_non_utf8 && !ValidateUTF8(attribute_)) {
+          return Error("illegal UTF-8 sequence");
+        }
         token_ = kTokenStringConstant;
         return NoError();
       }
@@ -338,6 +352,7 @@
           cursor_++;
           // TODO: make nested.
           while (*cursor_ != '*' || cursor_[1] != '/') {
+            if (*cursor_ == '\n') line_++;
             if (!*cursor_) return Error("end of file in comment");
             cursor_++;
           }
@@ -433,7 +448,7 @@
               cursor_++;
               while (isxdigit(static_cast<unsigned char>(*cursor_))) cursor_++;
               attribute_.append(start + 2, cursor_);
-              attribute_ = NumToString(StringToUInt(attribute_.c_str(), 16));
+              attribute_ = NumToString(StringToUInt(attribute_.c_str(), nullptr, 16));
               token_ = kTokenIntegerConstant;
               return NoError();
           }
@@ -643,6 +658,11 @@
               "only int, uint, long and ulong data types support hashing.");
     }
   }
+  auto cpp_type = field->attributes.Lookup("cpp_type");
+  if (cpp_type) {
+    if (!hash_name)
+      return Error("cpp_type can only be used with a hashed field");
+  }
   if (field->deprecated && struct_def.fixed)
     return Error("can't deprecate fields in a struct");
   field->required = field->attributes.Lookup("required") != nullptr;
@@ -660,6 +680,11 @@
         return Error("'key' field must be string or scalar type");
     }
   }
+
+  field->native_inline = field->attributes.Lookup("native_inline") != nullptr;
+  if (field->native_inline && !IsStruct(field->value.type))
+    return Error("native_inline can only be defined on structs'");
+
   auto nested = field->attributes.Lookup("nested_flatbuffer");
   if (nested) {
     if (nested->type.base_type != BASE_TYPE_STRING)
@@ -1079,10 +1104,15 @@
       NEXT();
     } else {  // Numeric constant in string.
       if (IsInteger(e.type.base_type)) {
-        // TODO(wvo): do we want to check for garbage after the number?
-        e.constant = NumToString(StringToInt(attribute_.c_str()));
+        char *end;
+        e.constant = NumToString(StringToInt(attribute_.c_str(), &end));
+        if (*end)
+          return Error("invalid integer: " + attribute_);
       } else if (IsFloat(e.type.base_type)) {
-        e.constant = NumToString(strtod(attribute_.c_str(), nullptr));
+        char *end;
+        e.constant = NumToString(strtod(attribute_.c_str(), &end));
+        if (*end)
+          return Error("invalid float: " + attribute_);
       } else {
         assert(0);  // Shouldn't happen, we covered all types.
         e.constant = "0";
@@ -1216,10 +1246,12 @@
       EXPECT(kTokenIdentifier);
       if (is_union) {
         ECHECK(ParseNamespacing(&full_name, &value_name));
-        // Since we can't namespace the actual enum identifiers, turn
-        // namespace parts into part of the identifier.
-        value_name = full_name;
-        std::replace(value_name.begin(), value_name.end(), '.', '_');
+        if (opts.union_value_namespacing) {
+          // Since we can't namespace the actual enum identifiers, turn
+          // namespace parts into part of the identifier.
+          value_name = full_name;
+          std::replace(value_name.begin(), value_name.end(), '.', '_');
+        }
       }
       auto prevsize = enum_def.vals.vec.size();
       auto value = enum_def.vals.vec.size()
@@ -1325,10 +1357,11 @@
     auto align = static_cast<size_t>(atoi(force_align->constant.c_str()));
     if (force_align->type.base_type != BASE_TYPE_INT ||
         align < struct_def->minalign ||
-        align > 16 ||
+        align > FLATBUFFERS_MAX_ALIGNMENT ||
         align & (align - 1))
       return Error("force_align must be a power of two integer ranging from the"
-            "struct\'s natural alignment to 16");
+                   "struct\'s natural alignment to " +
+                   NumToString(FLATBUFFERS_MAX_ALIGNMENT));
     struct_def->minalign = align;
   }
   struct_def->PadLastField(struct_def->minalign);
@@ -1961,7 +1994,8 @@
 // Schema serialization functionality:
 
 template<typename T> bool compareName(const T* a, const T* b) {
-    return a->name < b->name;
+    return a->defined_namespace->GetFullyQualifiedName(a->name)
+        < b->defined_namespace->GetFullyQualifiedName(b->name);
 }
 
 template<typename T> void AssignIndices(const std::vector<T *> &defvec) {
@@ -2007,8 +2041,9 @@
       (*it)->Serialize(builder,
                        static_cast<uint16_t>(it - fields.vec.begin()), parser));
   }
+  auto qualified_name = defined_namespace->GetFullyQualifiedName(name);
   return reflection::CreateObject(*builder,
-                                  builder->CreateString(name),
+                                  builder->CreateString(qualified_name),
                                   builder->CreateVectorOfSortedTables(
                                     &field_offsets),
                                   fixed,
@@ -2045,8 +2080,9 @@
   for (auto it = vals.vec.begin(); it != vals.vec.end(); ++it) {
     enumval_offsets.push_back((*it)->Serialize(builder));
   }
+  auto qualified_name = defined_namespace->GetFullyQualifiedName(name);
   return reflection::CreateEnum(*builder,
-                                builder->CreateString(name),
+                                builder->CreateString(qualified_name),
                                 builder->CreateVector(enumval_offsets),
                                 is_union,
                                 underlying_type.Serialize(builder),
@@ -2093,4 +2129,57 @@
   }
 }
 
+std::string Parser::ConformTo(const Parser &base) {
+  for (auto sit = structs_.vec.begin(); sit != structs_.vec.end(); ++sit) {
+    auto &struct_def = **sit;
+    auto qualified_name =
+        struct_def.defined_namespace->GetFullyQualifiedName(struct_def.name);
+    auto struct_def_base = base.structs_.Lookup(qualified_name);
+    if (!struct_def_base) continue;
+    for (auto fit = struct_def.fields.vec.begin();
+             fit != struct_def.fields.vec.end(); ++fit) {
+      auto &field = **fit;
+      auto field_base = struct_def_base->fields.Lookup(field.name);
+      if (field_base) {
+        if (field.value.offset != field_base->value.offset)
+          return "offsets differ for field: " + field.name;
+        if (field.value.constant != field_base->value.constant)
+          return "defaults differ for field: " + field.name;
+        if (!EqualByName(field.value.type, field_base->value.type))
+          return "types differ for field: " + field.name;
+      } else {
+        // Doesn't have to exist, deleting fields is fine.
+        // But we should check if there is a field that has the same offset
+        // but is incompatible (in the case of field renaming).
+        for (auto fbit = struct_def_base->fields.vec.begin();
+                 fbit != struct_def_base->fields.vec.end(); ++fbit) {
+          field_base = *fbit;
+          if (field.value.offset == field_base->value.offset) {
+            if (!EqualByName(field.value.type, field_base->value.type))
+              return "field renamed to different type: " + field.name;
+            break;
+          }
+        }
+      }
+    }
+  }
+  for (auto eit = enums_.vec.begin(); eit != enums_.vec.end(); ++eit) {
+    auto &enum_def = **eit;
+    auto qualified_name =
+        enum_def.defined_namespace->GetFullyQualifiedName(enum_def.name);
+    auto enum_def_base = base.enums_.Lookup(qualified_name);
+    if (!enum_def_base) continue;
+    for (auto evit = enum_def.vals.vec.begin();
+             evit != enum_def.vals.vec.end(); ++evit) {
+      auto &enum_val = **evit;
+      auto enum_val_base = enum_def_base->vals.Lookup(enum_val.name);
+      if (enum_val_base) {
+        if (enum_val.value != enum_val_base->value)
+          return "values differ for enum: " + enum_val.name;
+      }
+    }
+  }
+  return "";
+}
+
 }  // namespace flatbuffers
diff --git a/src/reflection.cpp b/src/reflection.cpp
index ff499ae..e5f45dc 100644
--- a/src/reflection.cpp
+++ b/src/reflection.cpp
@@ -180,7 +180,8 @@
   // Check if the range between first (lower address) and second straddles
   // the insertion point. If it does, change the offset at offsetloc (of
   // type T, with direction D).
-  template<typename T, int D> void Straddle(void *first, void *second,
+  template<typename T, int D> void Straddle(const void *first,
+                                            const void *second,
                                             void *offsetloc) {
     if (first <= startptr_ && second >= startptr_) {
       WriteScalar<T>(offsetloc, ReadScalar<T>(offsetloc) + delta_ * D);
@@ -194,9 +195,9 @@
   // resize actually happens.
   // This must be checked for every offset, since we can't know which offsets
   // will straddle and which won't.
-  uint8_t &DagCheck(void *offsetloc) {
-    auto dag_idx = reinterpret_cast<uoffset_t *>(offsetloc) -
-                   reinterpret_cast<uoffset_t *>(buf_.data());
+  uint8_t &DagCheck(const void *offsetloc) {
+    auto dag_idx = reinterpret_cast<const uoffset_t *>(offsetloc) -
+                   reinterpret_cast<const uoffset_t *>(buf_.data());
     return dag_check_[dag_idx];
   }
 
@@ -204,72 +205,76 @@
     if (DagCheck(table))
       return;  // Table already visited.
     auto vtable = table->GetVTable();
-    // Check if the vtable offset points beyond the insertion point.
-    Straddle<soffset_t, -1>(table, vtable, table);
-    // This direction shouldn't happen because vtables that sit before tables
-    // are always directly adjacent, but check just in case we ever change the
-    // way flatbuffers are built.
-    Straddle<soffset_t, -1>(vtable, table, table);
     // Early out: since all fields inside the table must point forwards in
     // memory, if the insertion point is before the table we can stop here.
     auto tableloc = reinterpret_cast<uint8_t *>(table);
-    if (startptr_ <= tableloc) return;
-    // Check each field.
-    auto fielddefs = objectdef.fields();
-    for (auto it = fielddefs->begin(); it != fielddefs->end(); ++it) {
-      auto &fielddef = **it;
-      auto base_type = fielddef.type()->base_type();
-      // Ignore scalars.
-      if (base_type <= reflection::Double) continue;
-      // Ignore fields that are not stored.
-      auto offset = table->GetOptionalFieldOffset(fielddef.offset());
-      if (!offset) continue;
-      // Ignore structs.
-      auto subobjectdef = base_type == reflection::Obj ?
-        schema_.objects()->Get(fielddef.type()->index()) : nullptr;
-      if (subobjectdef && subobjectdef->is_struct()) continue;
-      // Get this fields' offset, and read it if safe.
-      auto offsetloc = tableloc + offset;
-      if (DagCheck(offsetloc))
-        continue;  // This offset already visited.
-      auto ref = offsetloc + ReadScalar<uoffset_t>(offsetloc);
-      Straddle<uoffset_t, 1>(offsetloc, ref, offsetloc);
-      // Recurse.
-      switch (base_type) {
-        case reflection::Obj: {
-          ResizeTable(*subobjectdef, reinterpret_cast<Table *>(ref));
-          break;
-        }
-        case reflection::Vector: {
-          auto elem_type = fielddef.type()->element();
-          if (elem_type != reflection::Obj && elem_type != reflection::String)
+    if (startptr_ <= tableloc) {
+      // Check if insertion point is between the table and a vtable that
+      // precedes it. This can't happen in current construction code, but check
+      // just in case we ever change the way flatbuffers are built.
+      Straddle<soffset_t, -1>(vtable, table, table);
+    } else {
+      // Check each field.
+      auto fielddefs = objectdef.fields();
+      for (auto it = fielddefs->begin(); it != fielddefs->end(); ++it) {
+        auto &fielddef = **it;
+        auto base_type = fielddef.type()->base_type();
+        // Ignore scalars.
+        if (base_type <= reflection::Double) continue;
+        // Ignore fields that are not stored.
+        auto offset = table->GetOptionalFieldOffset(fielddef.offset());
+        if (!offset) continue;
+        // Ignore structs.
+        auto subobjectdef = base_type == reflection::Obj ?
+          schema_.objects()->Get(fielddef.type()->index()) : nullptr;
+        if (subobjectdef && subobjectdef->is_struct()) continue;
+        // Get this fields' offset, and read it if safe.
+        auto offsetloc = tableloc + offset;
+        if (DagCheck(offsetloc))
+          continue;  // This offset already visited.
+        auto ref = offsetloc + ReadScalar<uoffset_t>(offsetloc);
+        Straddle<uoffset_t, 1>(offsetloc, ref, offsetloc);
+        // Recurse.
+        switch (base_type) {
+          case reflection::Obj: {
+            ResizeTable(*subobjectdef, reinterpret_cast<Table *>(ref));
             break;
-          auto vec = reinterpret_cast<Vector<uoffset_t> *>(ref);
-          auto elemobjectdef = elem_type == reflection::Obj
-            ? schema_.objects()->Get(fielddef.type()->index())
-            : nullptr;
-          if (elemobjectdef && elemobjectdef->is_struct()) break;
-          for (uoffset_t i = 0; i < vec->size(); i++) {
-            auto loc = vec->Data() + i * sizeof(uoffset_t);
-            if (DagCheck(loc))
-              continue;  // This offset already visited.
-            auto dest = loc + vec->Get(i);
-            Straddle<uoffset_t, 1>(loc, dest ,loc);
-            if (elemobjectdef)
-              ResizeTable(*elemobjectdef, reinterpret_cast<Table *>(dest));
           }
-          break;
+          case reflection::Vector: {
+            auto elem_type = fielddef.type()->element();
+            if (elem_type != reflection::Obj && elem_type != reflection::String)
+              break;
+            auto vec = reinterpret_cast<Vector<uoffset_t> *>(ref);
+            auto elemobjectdef = elem_type == reflection::Obj
+              ? schema_.objects()->Get(fielddef.type()->index())
+              : nullptr;
+            if (elemobjectdef && elemobjectdef->is_struct()) break;
+            for (uoffset_t i = 0; i < vec->size(); i++) {
+              auto loc = vec->Data() + i * sizeof(uoffset_t);
+              if (DagCheck(loc))
+                continue;  // This offset already visited.
+              auto dest = loc + vec->Get(i);
+              Straddle<uoffset_t, 1>(loc, dest ,loc);
+              if (elemobjectdef)
+                ResizeTable(*elemobjectdef, reinterpret_cast<Table *>(dest));
+            }
+            break;
+          }
+          case reflection::Union: {
+            ResizeTable(GetUnionType(schema_, objectdef, fielddef, *table),
+                        reinterpret_cast<Table *>(ref));
+            break;
+          }
+          case reflection::String:
+            break;
+          default:
+            assert(false);
         }
-        case reflection::Union: {
-          ResizeTable(GetUnionType(schema_, objectdef, fielddef, *table),
-                      reinterpret_cast<Table *>(ref));
-          break;
-        }
-        case reflection::String:
-          break;
-        default:
-          assert(false);
       }
+      // Check if the vtable offset points beyond the insertion point.
+      // Must do this last, since GetOptionalFieldOffset above still reads
+      // this value.
+      Straddle<soffset_t, -1>(table, vtable, table);
     }
   }
 
diff --git a/tests/FlatBuffers.Test/ByteBufferTests.cs b/tests/FlatBuffers.Test/ByteBufferTests.cs
index b86c365..3324f12 100644
--- a/tests/FlatBuffers.Test/ByteBufferTests.cs
+++ b/tests/FlatBuffers.Test/ByteBufferTests.cs
@@ -40,6 +40,7 @@
             Assert.AreEqual((byte)99, buffer[0]);
         }
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutByteCannotPutAtOffsetPastLength()
         {
@@ -47,6 +48,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.PutByte(1, 99));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutShortPopulatesBufferCorrectly()
@@ -60,6 +62,7 @@
             Assert.AreEqual((byte)0, buffer[1]);
         }
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutShortCannotPutAtOffsetPastLength()
         {
@@ -67,7 +70,9 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.PutShort(2, 99));
         }
+#endif
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutShortChecksLength()
         {
@@ -83,6 +88,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.PutShort(1, 99));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutIntPopulatesBufferCorrectly()
@@ -98,6 +104,7 @@
             Assert.AreEqual(0x0A, buffer[3]);
         }
 
+ #if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutIntCannotPutAtOffsetPastLength()
         {
@@ -121,6 +128,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.PutInt(2, 0x0A0B0C0D));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutLongPopulatesBufferCorrectly()
@@ -140,6 +148,7 @@
             Assert.AreEqual(0x01, buffer[7]);
         }
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_PutLongCannotPutAtOffsetPastLength()
         {
@@ -163,6 +172,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.PutLong(2, 0x010203040A0B0C0D));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetByteReturnsCorrectData()
@@ -173,6 +183,7 @@
             Assert.AreEqual((byte)99, uut.Get(0));
         }
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetByteChecksOffset()
         {
@@ -180,6 +191,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(()=>uut.Get(1));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetShortReturnsCorrectData()
@@ -191,6 +203,7 @@
             Assert.AreEqual(1, uut.GetShort(0));
         }
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetShortChecksOffset()
         {
@@ -206,6 +219,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.GetShort(1));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetIntReturnsCorrectData()
@@ -219,6 +233,7 @@
             Assert.AreEqual(0x0A0B0C0D, uut.GetInt(0));
         }
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetIntChecksOffset()
         {
@@ -234,6 +249,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.GetInt(0));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetLongReturnsCorrectData()
@@ -251,6 +267,7 @@
             Assert.AreEqual(0x010203040A0B0C0D, uut.GetLong(0));
         }
 
+#if !BYTEBUFFER_NO_BOUNDS_CHECK
         [FlatBuffersTestMethod]
         public void ByteBuffer_GetLongChecksOffset()
         {
@@ -266,6 +283,7 @@
             var uut = new ByteBuffer(buffer);
             Assert.Throws<ArgumentOutOfRangeException>(() => uut.GetLong(0));
         }
+#endif
 
         [FlatBuffersTestMethod]
         public void ByteBuffer_ReverseBytesUshort()
diff --git a/tests/FlatBuffers.Test/FlatBuffers.Test.csproj b/tests/FlatBuffers.Test/FlatBuffers.Test.csproj
index cc7c5cf..6e76b07 100644
--- a/tests/FlatBuffers.Test/FlatBuffers.Test.csproj
+++ b/tests/FlatBuffers.Test/FlatBuffers.Test.csproj
@@ -1,4 +1,4 @@
-<?xml version="1.0" encoding="utf-8"?>
+<?xml version="1.0" encoding="utf-8"?>
 <Project ToolsVersion="12.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
   <PropertyGroup>
     <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
@@ -41,6 +41,9 @@
     <Compile Include="..\..\net\FlatBuffers\ByteBuffer.cs">
       <Link>FlatBuffers\ByteBuffer.cs</Link>
     </Compile>
+    <Compile Include="..\..\net\FlatBuffers\IFlatbufferObject.cs">
+      <Link>FlatBuffers\IFlatbufferObject.cs</Link>
+    </Compile>
     <Compile Include="..\..\net\FlatBuffers\Offset.cs">
       <Link>FlatBuffers\Offset.cs</Link>
     </Compile>
@@ -116,4 +119,4 @@
   <Target Name="AfterBuild">
   </Target>
   -->
-</Project>
\ No newline at end of file
+</Project>
diff --git a/tests/FlatBuffers.Test/FlatBuffersExampleTests.cs b/tests/FlatBuffers.Test/FlatBuffersExampleTests.cs
index 80791dd..d032d7e 100644
--- a/tests/FlatBuffers.Test/FlatBuffersExampleTests.cs
+++ b/tests/FlatBuffers.Test/FlatBuffersExampleTests.cs
@@ -39,6 +39,19 @@
             // better for performance.
             var fbb = new FlatBufferBuilder(1);
 
+            StringOffset[] names = { fbb.CreateString("Frodo"), fbb.CreateString("Barney"), fbb.CreateString("Wilma") };
+            Offset<Monster>[] off = new Offset<Monster>[3];
+            Monster.StartMonster(fbb);
+            Monster.AddName(fbb, names[0]);
+            off[0] = Monster.EndMonster(fbb);
+            Monster.StartMonster(fbb);
+            Monster.AddName(fbb, names[1]);
+            off[1] = Monster.EndMonster(fbb);
+            Monster.StartMonster(fbb);
+            Monster.AddName(fbb, names[2]);
+            off[2] = Monster.EndMonster(fbb);
+            var sortMons = Monster.CreateMySortedVectorOfTables(fbb, off);
+
             // We set up the same values as monsterdata.json:
 
             var str = fbb.CreateString("MyMonster");
@@ -79,6 +92,7 @@
             Monster.AddTest4(fbb, test4);
             Monster.AddTestarrayofstring(fbb, testArrayOfString);
             Monster.AddTestbool(fbb, false);
+            Monster.AddTestarrayoftables(fbb, sortMons);
             var mon = Monster.EndMonster(fbb);
 
             Monster.FinishMonsterBuffer(fbb, mon);
@@ -103,6 +117,16 @@
             Assert.AreEqual(monster.MutateMana((short)10), false);
             Assert.AreEqual(monster.Mana, (short)150);
 
+            // Accessing a vector of sorted by the key tables
+            Assert.AreEqual(monster.Testarrayoftables(0).Value.Name, "Barney");
+            Assert.AreEqual(monster.Testarrayoftables(1).Value.Name, "Frodo");
+            Assert.AreEqual(monster.Testarrayoftables(2).Value.Name, "Wilma");
+
+            // Example of searching for a table by the key
+            Assert.IsTrue(Monster.LookupByKey(sortMons, "Frodo", fbb.DataBuffer) != null);
+            Assert.IsTrue(Monster.LookupByKey(sortMons, "Barney", fbb.DataBuffer) != null);
+            Assert.IsTrue(Monster.LookupByKey(sortMons, "Wilma", fbb.DataBuffer)!= null);
+
             // testType is an existing field and mutating it should succeed
             Assert.AreEqual(monster.TestType, Any.Monster);
             Assert.AreEqual(monster.MutateTestType(Any.NONE), true);
@@ -119,7 +143,7 @@
 
             for (int i = 0; i < monster.InventoryLength; i++)
             {
-                Assert.AreEqual(monster.GetInventory(i), i + 1);
+                Assert.AreEqual(monster.Inventory(i), i + 1);
             }
 
             //reverse mutation
@@ -130,7 +154,7 @@
             Assert.AreEqual(monster.MutateInventory(4, 4), true);
 
             // get a struct field and edit one of its fields
-            Vec3 pos = monster.Pos;
+            Vec3 pos = (Vec3)monster.Pos;
             Assert.AreEqual(pos.X, 1.0f);
             pos.MutateX(55.0f);
             Assert.AreEqual(pos.X, 55.0f);
@@ -148,21 +172,20 @@
             Assert.AreEqual(150, monster.Mana);
             Assert.AreEqual("MyMonster", monster.Name);
 
-            var pos = monster.Pos;
+            var pos = monster.Pos.Value;
             Assert.AreEqual(1.0f, pos.X);
             Assert.AreEqual(2.0f, pos.Y);
             Assert.AreEqual(3.0f, pos.Z);
 
             Assert.AreEqual(3.0f, pos.Test1);
             Assert.AreEqual(Color.Green, pos.Test2);
-            var t = pos.Test3;
+            var t = (MyGame.Example.Test)pos.Test3;
             Assert.AreEqual((short)5, t.A);
             Assert.AreEqual((sbyte)6, t.B);
 
             Assert.AreEqual(Any.Monster, monster.TestType);
 
-            var monster2 = new Monster();
-            Assert.IsTrue(monster.GetTest(monster2) != null);
+            var monster2 = monster.Test<Monster>().Value;
             Assert.AreEqual("Fred", monster2.Name);
 
 
@@ -170,19 +193,19 @@
             var invsum = 0;
             for (var i = 0; i < monster.InventoryLength; i++)
             {
-                invsum += monster.GetInventory(i);
+                invsum += monster.Inventory(i);
             }
             Assert.AreEqual(10, invsum);
 
-            var test0 = monster.GetTest4(0);
-            var test1 = monster.GetTest4(1);
+            var test0 = monster.Test4(0).Value;
+            var test1 = monster.Test4(1).Value;
             Assert.AreEqual(2, monster.Test4Length);
 
             Assert.AreEqual(100, test0.A + test0.B + test1.A + test1.B);
 
             Assert.AreEqual(2, monster.TestarrayofstringLength);
-            Assert.AreEqual("test1", monster.GetTestarrayofstring(0));
-            Assert.AreEqual("test2", monster.GetTestarrayofstring(1));
+            Assert.AreEqual("test1", monster.Testarrayofstring(0));
+            Assert.AreEqual("test2", monster.Testarrayofstring(1));
 
             Assert.AreEqual(false, monster.Testbool);
 
@@ -245,10 +268,10 @@
             Monster.AddTestnestedflatbuffer(fbb2, nestedBuffer);
             var monster = Monster.EndMonster(fbb2);
             Monster.FinishMonsterBuffer(fbb2, monster);
-            
+
             // Now test the data extracted from the nested buffer
             var mons = Monster.GetRootAsMonster(fbb2.DataBuffer);
-            var nestedMonster = mons.TestnestedflatbufferAsMonster();
+            var nestedMonster = mons.GetTestnestedflatbufferAsMonster().Value;
 
             Assert.AreEqual(nestedMonsterMana, nestedMonster.Mana);
             Assert.AreEqual(nestedMonsterHp, nestedMonster.Hp);
diff --git a/tests/FlatBuffers.Test/TestTable.cs b/tests/FlatBuffers.Test/TestTable.cs
index c51237b..2b506b6 100644
--- a/tests/FlatBuffers.Test/TestTable.cs
+++ b/tests/FlatBuffers.Test/TestTable.cs
@@ -19,133 +19,135 @@
     /// <summary>
     /// A test Table object that gives easy access to the slot data
     /// </summary>
-    internal class TestTable : Table
+    internal struct TestTable
     {
+        Table t;
+
         public TestTable(ByteBuffer bb, int pos)
         {
-            base.bb = bb;
-            base.bb_pos = pos;
+            t.bb = bb;
+            t.bb_pos = pos;
         }
 
         public bool GetSlot(int slot, bool def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetSbyte(bb_pos + off) != 0;
+            return t.bb.GetSbyte(t.bb_pos + off) != 0;
         }
 
         public sbyte GetSlot(int slot, sbyte def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetSbyte(bb_pos + off);
+            return t.bb.GetSbyte(t.bb_pos + off);
         }
 
         public byte GetSlot(int slot, byte def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.Get(bb_pos + off);
+            return t.bb.Get(t.bb_pos + off);
         }
 
         public short GetSlot(int slot, short def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetShort(bb_pos + off);
+            return t.bb.GetShort(t.bb_pos + off);
         }
 
         public ushort GetSlot(int slot, ushort def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetUshort(bb_pos + off);
+            return t.bb.GetUshort(t.bb_pos + off);
         }
 
         public int GetSlot(int slot, int def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetInt(bb_pos + off);
+            return t.bb.GetInt(t.bb_pos + off);
         }
 
         public uint GetSlot(int slot, uint def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetUint(bb_pos + off);
+            return t.bb.GetUint(t.bb_pos + off);
         }
 
         public long GetSlot(int slot, long def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetLong(bb_pos + off);
+            return t.bb.GetLong(t.bb_pos + off);
         }
 
         public ulong GetSlot(int slot, ulong def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetUlong(bb_pos + off);
+            return t.bb.GetUlong(t.bb_pos + off);
         }
 
         public float GetSlot(int slot, float def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetFloat(bb_pos + off);
+            return t.bb.GetFloat(t.bb_pos + off);
         }
 
         public double GetSlot(int slot, double def)
         {
-            var off = base.__offset(slot);
+            var off = t.__offset(slot);
 
             if (off == 0)
             {
                 return def;
             }
-            return bb.GetDouble(bb_pos + off);
+            return t.bb.GetDouble(t.bb_pos + off);
         }
     }
-}
\ No newline at end of file
+}
diff --git a/tests/GoTest.sh b/tests/GoTest.sh
index 353930a..7be4aff 100755
--- a/tests/GoTest.sh
+++ b/tests/GoTest.sh
@@ -29,9 +29,9 @@
 mkdir -p ${go_src}/github.com/google/flatbuffers/go
 mkdir -p ${go_src}/flatbuffers_test
 
-cp -u MyGame/Example/*.go ./go_gen/src/MyGame/Example/
-cp -u ../go/* ./go_gen/src/github.com/google/flatbuffers/go
-cp -u ./go_test.go ./go_gen/src/flatbuffers_test/
+cp -a MyGame/Example/*.go ./go_gen/src/MyGame/Example/
+cp -a ../go/* ./go_gen/src/github.com/google/flatbuffers/go
+cp -a ./go_test.go ./go_gen/src/flatbuffers_test/
 
 # Run tests with necessary flags.
 # Developers may wish to see more detail by appending the verbosity flag
@@ -50,6 +50,18 @@
                      --fuzz_fields=4 \
                      --fuzz_objects=10000
 
+GO_TEST_RESULT=$?
 rm -rf ${go_path}/{pkg,src}
+if [[ $GO_TEST_RESULT  == 0 ]]; then
+    echo "OK: Go tests passed."
+else
+    echo "KO: Go tests failed."
+    exit 1
+fi
 
-echo "OK: Go tests passed."
+NOT_FMT_FILES=$(gofmt -l MyGame)
+if [[ ${NOT_FMT_FILES} != "" ]]; then
+    echo "These files are not well gofmt'ed:\n\n${NOT_FMT_FILES}"
+    # enable this when enums are properly formated
+    # exit 1
+fi
diff --git a/tests/JavaScriptTest.js b/tests/JavaScriptTest.js
index c89ae85..c97ed2d 100644
--- a/tests/JavaScriptTest.js
+++ b/tests/JavaScriptTest.js
@@ -64,7 +64,10 @@
 
   fs.writeFileSync('monsterdata_javascript_wire.mon', new Buffer(fbb.asUint8Array()));
 
-  // Test it:
+  // Tests mutation first.  This will verify that we did not trample any other
+  // part of the byte buffer.
+  testMutation(fbb.dataBuffer());
+  
   testBuffer(fbb.dataBuffer());
 
   test64bit();
@@ -74,6 +77,21 @@
   console.log('FlatBuffers test: completed successfully');
 }
 
+function testMutation(bb) {
+  var monster = MyGame.Example.Monster.getRootAsMonster(bb);
+
+  monster.mutate_hp(120);
+  assert.strictEqual(monster.hp(), 120);
+
+  monster.mutate_hp(80);
+  assert.strictEqual(monster.hp(), 80);
+
+  var manaRes = monster.mutate_mana(10);
+  assert.strictEqual(manaRes, false);  // Field was NOT present, because default value.
+
+  // TODO: There is not the availability to mutate structs or vectors.
+}
+
 function testBuffer(bb) {
   assert.ok(MyGame.Example.Monster.bufferHasIdentifier(bb));
 
diff --git a/tests/JavaTest.java b/tests/JavaTest.java
index 154fdec..d53e973 100755
--- a/tests/JavaTest.java
+++ b/tests/JavaTest.java
@@ -51,6 +51,19 @@
         // better for performance.
         FlatBufferBuilder fbb = new FlatBufferBuilder(1);
 
+        int[] names = {fbb.createString("Frodo"), fbb.createString("Barney"), fbb.createString("Wilma")};
+        int[] off = new int[3];
+        Monster.startMonster(fbb);
+        Monster.addName(fbb, names[0]);
+        off[0] = Monster.endMonster(fbb);
+        Monster.startMonster(fbb);
+        Monster.addName(fbb, names[1]);
+        off[1] = Monster.endMonster(fbb);
+        Monster.startMonster(fbb);
+        Monster.addName(fbb, names[2]);
+        off[2] = Monster.endMonster(fbb);
+        int sortMons = fbb.createSortedVectorOfTables(new Monster(), off);
+		
         // We set up the same values as monsterdata.json:
 
         int str = fbb.createString("MyMonster");
@@ -84,6 +97,7 @@
         Monster.addTestarrayofstring(fbb, testArrayOfString);
         Monster.addTestbool(fbb, false);
         Monster.addTesthashu32Fnv1(fbb, Integer.MAX_VALUE + 1L);
+        Monster.addTestarrayoftables(fbb, sortMons);
         int mon = Monster.endMonster(fbb);
 
         Monster.finishMonsterBuffer(fbb, mon);
@@ -121,6 +135,16 @@
         // the mana field should retain its default value
         TestEq(monster.mutateMana((short)10), false);
         TestEq(monster.mana(), (short)150);
+		
+		// Accessing a vector of sorted by the key tables
+        TestEq(monster.testarrayoftables(0).name(), "Barney");
+        TestEq(monster.testarrayoftables(1).name(), "Frodo");
+        TestEq(monster.testarrayoftables(2).name(), "Wilma");
+		
+		// Example of searching for a table by the key
+        TestEq(Monster.lookupByKey(sortMons, "Frodo", fbb.dataBuffer()).name(), "Frodo");
+        TestEq(Monster.lookupByKey(sortMons, "Barney", fbb.dataBuffer()).name(), "Barney");
+        TestEq(Monster.lookupByKey(sortMons, "Wilma", fbb.dataBuffer()).name(), "Wilma");
 
         // testType is an existing field and mutating it should succeed
         TestEq(monster.testType(), (byte)Any.Monster);
@@ -161,6 +185,10 @@
 
         TestNestedFlatBuffer();
 
+        TestCreateByteVector();
+
+        TestCreateUninitializedVector();
+
         System.out.println("FlatBuffers test: completed successfully");
     }
 
@@ -281,6 +309,44 @@
         TestEq(nestedMonsterName, nestedMonster.name());
     }
 
+    static void TestCreateByteVector() {
+        FlatBufferBuilder fbb = new FlatBufferBuilder(16);
+        int str = fbb.createString("MyMonster");
+        byte[] inventory = new byte[] { 0, 1, 2, 3, 4 };
+        int vec = fbb.createByteVector(inventory);
+        Monster.startMonster(fbb);
+        Monster.addInventory(fbb, vec);
+        Monster.addName(fbb, str);
+        int monster1 = Monster.endMonster(fbb);
+        Monster.finishMonsterBuffer(fbb, monster1);
+        Monster monsterObject = Monster.getRootAsMonster(fbb.dataBuffer());
+
+        TestEq(monsterObject.inventory(1), (int)inventory[1]);
+        TestEq(monsterObject.inventoryLength(), inventory.length);
+        TestEq(ByteBuffer.wrap(inventory), monsterObject.inventoryAsByteBuffer());
+    }
+
+    static void TestCreateUninitializedVector() {
+        FlatBufferBuilder fbb = new FlatBufferBuilder(16);
+        int str = fbb.createString("MyMonster");
+        byte[] inventory = new byte[] { 0, 1, 2, 3, 4 };
+        ByteBuffer bb = fbb.createUnintializedVector(1, inventory.length, 1);
+        for (byte i:inventory) {
+            bb.put(i);
+        }
+        int vec = fbb.endVector();
+        Monster.startMonster(fbb);
+        Monster.addInventory(fbb, vec);
+        Monster.addName(fbb, str);
+        int monster1 = Monster.endMonster(fbb);
+        Monster.finishMonsterBuffer(fbb, monster1);
+        Monster monsterObject = Monster.getRootAsMonster(fbb.dataBuffer());
+
+        TestEq(monsterObject.inventory(1), (int)inventory[1]);
+        TestEq(monsterObject.inventoryLength(), inventory.length);
+        TestEq(ByteBuffer.wrap(inventory), monsterObject.inventoryAsByteBuffer());
+    }
+
     static <T> void TestEq(T a, T b) {
         if (!a.equals(b)) {
             System.out.println("" + a.getClass().getName() + " " + b.getClass().getName());
diff --git a/tests/JavaTest.sh b/tests/JavaTest.sh
index 344bd1c..40e854b 100755
--- a/tests/JavaTest.sh
+++ b/tests/JavaTest.sh
@@ -1,4 +1,4 @@
-#!/bin/sh
+#!/bin/bash
 #
 # Copyright 2014 Google Inc. All rights reserved.
 #
@@ -16,14 +16,29 @@
 
 echo Compile then run the Java test.
 
+java -version
+
 testdir=$(readlink -fn `dirname $0`)
 thisdir=$(readlink -fn `pwd`)
 
+targetdir=${testdir}/target
+
 if [[ "$testdir" != "$thisdir" ]]; then
 	echo error: must be run from inside the ${testdir} directory
 	echo you ran it from ${thisdir}
 	exit 1
 fi
 
-javac -classpath ${testdir}/../java:${testdir}:${testdir}/namespace_test JavaTest.java
-java -classpath ${testdir}/../java:${testdir}:${testdir}/namespace_test JavaTest
+find .. -type f -name "*.class" -exec rm  {} \;
+
+if [[ -e "${targetdir}" ]]; then
+    echo "clean target"
+    rm -rf ${targetdir}
+fi
+
+mkdir ${targetdir}
+
+javac -d ${targetdir} -classpath ${testdir}/../java:${testdir}:${testdir}/namespace_test JavaTest.java
+java -classpath ${targetdir} JavaTest
+
+rm -rf ${targetdir}
diff --git a/tests/MyGame/Example/Any.go b/tests/MyGame/Example/Any.go
index df9f823..d69b141 100644
--- a/tests/MyGame/Example/Any.go
+++ b/tests/MyGame/Example/Any.go
@@ -8,3 +8,11 @@
 	AnyTestSimpleTableWithEnum = 2
 	AnyMyGame_Example2_Monster = 3
 )
+
+var EnumNamesAny = map[int]string{
+	AnyNONE:"NONE",
+	AnyMonster:"Monster",
+	AnyTestSimpleTableWithEnum:"TestSimpleTableWithEnum",
+	AnyMyGame_Example2_Monster:"MyGame_Example2_Monster",
+}
+
diff --git a/tests/MyGame/Example/Color.go b/tests/MyGame/Example/Color.go
index 09f6d58..d1eac54 100644
--- a/tests/MyGame/Example/Color.go
+++ b/tests/MyGame/Example/Color.go
@@ -7,3 +7,10 @@
 	ColorGreen = 2
 	ColorBlue = 8
 )
+
+var EnumNamesColor = map[int]string{
+	ColorRed:"Red",
+	ColorGreen:"Green",
+	ColorBlue:"Blue",
+}
+
diff --git a/tests/MyGame/Example/Monster.cs b/tests/MyGame/Example/Monster.cs
index fdfd2b0..30f4922 100644
--- a/tests/MyGame/Example/Monster.cs
+++ b/tests/MyGame/Example/Monster.cs
@@ -7,79 +7,77 @@
 using FlatBuffers;
 
 /// an example documentation comment: monster object
-public sealed class Monster : Table {
+public struct Monster : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static Monster GetRootAsMonster(ByteBuffer _bb) { return GetRootAsMonster(_bb, new Monster()); }
-  public static Monster GetRootAsMonster(ByteBuffer _bb, Monster obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public static bool MonsterBufferHasIdentifier(ByteBuffer _bb) { return __has_identifier(_bb, "MONS"); }
-  public Monster __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static Monster GetRootAsMonster(ByteBuffer _bb, Monster obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public static bool MonsterBufferHasIdentifier(ByteBuffer _bb) { return Table.__has_identifier(_bb, "MONS"); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public Monster __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public Vec3 Pos { get { return GetPos(new Vec3()); } }
-  public Vec3 GetPos(Vec3 obj) { int o = __offset(4); return o != 0 ? obj.__init(o + bb_pos, bb) : null; }
-  public short Mana { get { int o = __offset(6); return o != 0 ? bb.GetShort(o + bb_pos) : (short)150; } }
-  public bool MutateMana(short mana) { int o = __offset(6); if (o != 0) { bb.PutShort(o + bb_pos, mana); return true; } else { return false; } }
-  public short Hp { get { int o = __offset(8); return o != 0 ? bb.GetShort(o + bb_pos) : (short)100; } }
-  public bool MutateHp(short hp) { int o = __offset(8); if (o != 0) { bb.PutShort(o + bb_pos, hp); return true; } else { return false; } }
-  public string Name { get { int o = __offset(10); return o != 0 ? __string(o + bb_pos) : null; } }
-  public ArraySegment<byte>? GetNameBytes() { return __vector_as_arraysegment(10); }
-  public byte GetInventory(int j) { int o = __offset(14); return o != 0 ? bb.Get(__vector(o) + j * 1) : (byte)0; }
-  public int InventoryLength { get { int o = __offset(14); return o != 0 ? __vector_len(o) : 0; } }
-  public ArraySegment<byte>? GetInventoryBytes() { return __vector_as_arraysegment(14); }
-  public bool MutateInventory(int j, byte inventory) { int o = __offset(14); if (o != 0) { bb.Put(__vector(o) + j * 1, inventory); return true; } else { return false; } }
-  public Color Color { get { int o = __offset(16); return o != 0 ? (Color)bb.GetSbyte(o + bb_pos) : Color.Blue; } }
-  public bool MutateColor(Color color) { int o = __offset(16); if (o != 0) { bb.PutSbyte(o + bb_pos, (sbyte)color); return true; } else { return false; } }
-  public Any TestType { get { int o = __offset(18); return o != 0 ? (Any)bb.Get(o + bb_pos) : Any.NONE; } }
-  public bool MutateTestType(Any test_type) { int o = __offset(18); if (o != 0) { bb.Put(o + bb_pos, (byte)test_type); return true; } else { return false; } }
-  public TTable GetTest<TTable>(TTable obj) where TTable : Table { int o = __offset(20); return o != 0 ? __union(obj, o) : null; }
-  public Test GetTest4(int j) { return GetTest4(new Test(), j); }
-  public Test GetTest4(Test obj, int j) { int o = __offset(22); return o != 0 ? obj.__init(__vector(o) + j * 4, bb) : null; }
-  public int Test4Length { get { int o = __offset(22); return o != 0 ? __vector_len(o) : 0; } }
-  public string GetTestarrayofstring(int j) { int o = __offset(24); return o != 0 ? __string(__vector(o) + j * 4) : null; }
-  public int TestarrayofstringLength { get { int o = __offset(24); return o != 0 ? __vector_len(o) : 0; } }
+  public Vec3? Pos { get { int o = __p.__offset(4); return o != 0 ? (Vec3?)(new Vec3()).__assign(o + __p.bb_pos, __p.bb) : null; } }
+  public short Mana { get { int o = __p.__offset(6); return o != 0 ? __p.bb.GetShort(o + __p.bb_pos) : (short)150; } }
+  public bool MutateMana(short mana) { int o = __p.__offset(6); if (o != 0) { __p.bb.PutShort(o + __p.bb_pos, mana); return true; } else { return false; } }
+  public short Hp { get { int o = __p.__offset(8); return o != 0 ? __p.bb.GetShort(o + __p.bb_pos) : (short)100; } }
+  public bool MutateHp(short hp) { int o = __p.__offset(8); if (o != 0) { __p.bb.PutShort(o + __p.bb_pos, hp); return true; } else { return false; } }
+  public string Name { get { int o = __p.__offset(10); return o != 0 ? __p.__string(o + __p.bb_pos) : null; } }
+  public ArraySegment<byte>? GetNameBytes() { return __p.__vector_as_arraysegment(10); }
+  public byte Inventory(int j) { int o = __p.__offset(14); return o != 0 ? __p.bb.Get(__p.__vector(o) + j * 1) : (byte)0; }
+  public int InventoryLength { get { int o = __p.__offset(14); return o != 0 ? __p.__vector_len(o) : 0; } }
+  public ArraySegment<byte>? GetInventoryBytes() { return __p.__vector_as_arraysegment(14); }
+  public bool MutateInventory(int j, byte inventory) { int o = __p.__offset(14); if (o != 0) { __p.bb.Put(__p.__vector(o) + j * 1, inventory); return true; } else { return false; } }
+  public Color Color { get { int o = __p.__offset(16); return o != 0 ? (Color)__p.bb.GetSbyte(o + __p.bb_pos) : Color.Blue; } }
+  public bool MutateColor(Color color) { int o = __p.__offset(16); if (o != 0) { __p.bb.PutSbyte(o + __p.bb_pos, (sbyte)color); return true; } else { return false; } }
+  public Any TestType { get { int o = __p.__offset(18); return o != 0 ? (Any)__p.bb.Get(o + __p.bb_pos) : Any.NONE; } }
+  public bool MutateTestType(Any test_type) { int o = __p.__offset(18); if (o != 0) { __p.bb.Put(o + __p.bb_pos, (byte)test_type); return true; } else { return false; } }
+  public TTable? Test<TTable>() where TTable : struct, IFlatbufferObject { int o = __p.__offset(20); return o != 0 ? (TTable?)__p.__union<TTable>(o) : null; }
+  public Test? Test4(int j) { int o = __p.__offset(22); return o != 0 ? (Test?)(new Test()).__assign(__p.__vector(o) + j * 4, __p.bb) : null; }
+  public int Test4Length { get { int o = __p.__offset(22); return o != 0 ? __p.__vector_len(o) : 0; } }
+  public string Testarrayofstring(int j) { int o = __p.__offset(24); return o != 0 ? __p.__string(__p.__vector(o) + j * 4) : null; }
+  public int TestarrayofstringLength { get { int o = __p.__offset(24); return o != 0 ? __p.__vector_len(o) : 0; } }
   /// an example documentation comment: this will end up in the generated code
   /// multiline too
-  public Monster GetTestarrayoftables(int j) { return GetTestarrayoftables(new Monster(), j); }
-  public Monster GetTestarrayoftables(Monster obj, int j) { int o = __offset(26); return o != 0 ? obj.__init(__indirect(__vector(o) + j * 4), bb) : null; }
-  public int TestarrayoftablesLength { get { int o = __offset(26); return o != 0 ? __vector_len(o) : 0; } }
-  public Monster Enemy { get { return GetEnemy(new Monster()); } }
-  public Monster GetEnemy(Monster obj) { int o = __offset(28); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
-  public byte GetTestnestedflatbuffer(int j) { int o = __offset(30); return o != 0 ? bb.Get(__vector(o) + j * 1) : (byte)0; }
-  public int TestnestedflatbufferLength { get { int o = __offset(30); return o != 0 ? __vector_len(o) : 0; } }
-  public ArraySegment<byte>? GetTestnestedflatbufferBytes() { return __vector_as_arraysegment(30); }
-  public Monster TestnestedflatbufferAsMonster() { return GetTestnestedflatbufferAsMonster(new Monster()); }
-  public Monster GetTestnestedflatbufferAsMonster(Monster obj) { int o = __offset(30); return o != 0 ? obj.__init(__indirect(__vector(o)), bb) : null; }
-  public bool MutateTestnestedflatbuffer(int j, byte testnestedflatbuffer) { int o = __offset(30); if (o != 0) { bb.Put(__vector(o) + j * 1, testnestedflatbuffer); return true; } else { return false; } }
-  public Stat Testempty { get { return GetTestempty(new Stat()); } }
-  public Stat GetTestempty(Stat obj) { int o = __offset(32); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
-  public bool Testbool { get { int o = __offset(34); return o != 0 ? 0!=bb.Get(o + bb_pos) : (bool)false; } }
-  public bool MutateTestbool(bool testbool) { int o = __offset(34); if (o != 0) { bb.Put(o + bb_pos, (byte)(testbool ? 1 : 0)); return true; } else { return false; } }
-  public int Testhashs32Fnv1 { get { int o = __offset(36); return o != 0 ? bb.GetInt(o + bb_pos) : (int)0; } }
-  public bool MutateTesthashs32Fnv1(int testhashs32_fnv1) { int o = __offset(36); if (o != 0) { bb.PutInt(o + bb_pos, testhashs32_fnv1); return true; } else { return false; } }
-  public uint Testhashu32Fnv1 { get { int o = __offset(38); return o != 0 ? bb.GetUint(o + bb_pos) : (uint)0; } }
-  public bool MutateTesthashu32Fnv1(uint testhashu32_fnv1) { int o = __offset(38); if (o != 0) { bb.PutUint(o + bb_pos, testhashu32_fnv1); return true; } else { return false; } }
-  public long Testhashs64Fnv1 { get { int o = __offset(40); return o != 0 ? bb.GetLong(o + bb_pos) : (long)0; } }
-  public bool MutateTesthashs64Fnv1(long testhashs64_fnv1) { int o = __offset(40); if (o != 0) { bb.PutLong(o + bb_pos, testhashs64_fnv1); return true; } else { return false; } }
-  public ulong Testhashu64Fnv1 { get { int o = __offset(42); return o != 0 ? bb.GetUlong(o + bb_pos) : (ulong)0; } }
-  public bool MutateTesthashu64Fnv1(ulong testhashu64_fnv1) { int o = __offset(42); if (o != 0) { bb.PutUlong(o + bb_pos, testhashu64_fnv1); return true; } else { return false; } }
-  public int Testhashs32Fnv1a { get { int o = __offset(44); return o != 0 ? bb.GetInt(o + bb_pos) : (int)0; } }
-  public bool MutateTesthashs32Fnv1a(int testhashs32_fnv1a) { int o = __offset(44); if (o != 0) { bb.PutInt(o + bb_pos, testhashs32_fnv1a); return true; } else { return false; } }
-  public uint Testhashu32Fnv1a { get { int o = __offset(46); return o != 0 ? bb.GetUint(o + bb_pos) : (uint)0; } }
-  public bool MutateTesthashu32Fnv1a(uint testhashu32_fnv1a) { int o = __offset(46); if (o != 0) { bb.PutUint(o + bb_pos, testhashu32_fnv1a); return true; } else { return false; } }
-  public long Testhashs64Fnv1a { get { int o = __offset(48); return o != 0 ? bb.GetLong(o + bb_pos) : (long)0; } }
-  public bool MutateTesthashs64Fnv1a(long testhashs64_fnv1a) { int o = __offset(48); if (o != 0) { bb.PutLong(o + bb_pos, testhashs64_fnv1a); return true; } else { return false; } }
-  public ulong Testhashu64Fnv1a { get { int o = __offset(50); return o != 0 ? bb.GetUlong(o + bb_pos) : (ulong)0; } }
-  public bool MutateTesthashu64Fnv1a(ulong testhashu64_fnv1a) { int o = __offset(50); if (o != 0) { bb.PutUlong(o + bb_pos, testhashu64_fnv1a); return true; } else { return false; } }
-  public bool GetTestarrayofbools(int j) { int o = __offset(52); return o != 0 ? 0!=bb.Get(__vector(o) + j * 1) : false; }
-  public int TestarrayofboolsLength { get { int o = __offset(52); return o != 0 ? __vector_len(o) : 0; } }
-  public ArraySegment<byte>? GetTestarrayofboolsBytes() { return __vector_as_arraysegment(52); }
-  public bool MutateTestarrayofbools(int j, bool testarrayofbools) { int o = __offset(52); if (o != 0) { bb.Put(__vector(o) + j * 1, (byte)(testarrayofbools ? 1 : 0)); return true; } else { return false; } }
-  public float Testf { get { int o = __offset(54); return o != 0 ? bb.GetFloat(o + bb_pos) : (float)3.14159f; } }
-  public bool MutateTestf(float testf) { int o = __offset(54); if (o != 0) { bb.PutFloat(o + bb_pos, testf); return true; } else { return false; } }
-  public float Testf2 { get { int o = __offset(56); return o != 0 ? bb.GetFloat(o + bb_pos) : (float)3.0f; } }
-  public bool MutateTestf2(float testf2) { int o = __offset(56); if (o != 0) { bb.PutFloat(o + bb_pos, testf2); return true; } else { return false; } }
-  public float Testf3 { get { int o = __offset(58); return o != 0 ? bb.GetFloat(o + bb_pos) : (float)0.0f; } }
-  public bool MutateTestf3(float testf3) { int o = __offset(58); if (o != 0) { bb.PutFloat(o + bb_pos, testf3); return true; } else { return false; } }
-  public string GetTestarrayofstring2(int j) { int o = __offset(60); return o != 0 ? __string(__vector(o) + j * 4) : null; }
-  public int Testarrayofstring2Length { get { int o = __offset(60); return o != 0 ? __vector_len(o) : 0; } }
+  public Monster? Testarrayoftables(int j) { int o = __p.__offset(26); return o != 0 ? (Monster?)(new Monster()).__assign(__p.__indirect(__p.__vector(o) + j * 4), __p.bb) : null; }
+  public int TestarrayoftablesLength { get { int o = __p.__offset(26); return o != 0 ? __p.__vector_len(o) : 0; } }
+  public Monster? Enemy { get { int o = __p.__offset(28); return o != 0 ? (Monster?)(new Monster()).__assign(__p.__indirect(o + __p.bb_pos), __p.bb) : null; } }
+  public byte Testnestedflatbuffer(int j) { int o = __p.__offset(30); return o != 0 ? __p.bb.Get(__p.__vector(o) + j * 1) : (byte)0; }
+  public int TestnestedflatbufferLength { get { int o = __p.__offset(30); return o != 0 ? __p.__vector_len(o) : 0; } }
+  public ArraySegment<byte>? GetTestnestedflatbufferBytes() { return __p.__vector_as_arraysegment(30); }
+  public Monster? GetTestnestedflatbufferAsMonster() { int o = __p.__offset(30); return o != 0 ? (Monster?)(new Monster()).__assign(__p.__indirect(__p.__vector(o)), __p.bb) : null; }
+  public bool MutateTestnestedflatbuffer(int j, byte testnestedflatbuffer) { int o = __p.__offset(30); if (o != 0) { __p.bb.Put(__p.__vector(o) + j * 1, testnestedflatbuffer); return true; } else { return false; } }
+  public Stat? Testempty { get { int o = __p.__offset(32); return o != 0 ? (Stat?)(new Stat()).__assign(__p.__indirect(o + __p.bb_pos), __p.bb) : null; } }
+  public bool Testbool { get { int o = __p.__offset(34); return o != 0 ? 0!=__p.bb.Get(o + __p.bb_pos) : (bool)false; } }
+  public bool MutateTestbool(bool testbool) { int o = __p.__offset(34); if (o != 0) { __p.bb.Put(o + __p.bb_pos, (byte)(testbool ? 1 : 0)); return true; } else { return false; } }
+  public int Testhashs32Fnv1 { get { int o = __p.__offset(36); return o != 0 ? __p.bb.GetInt(o + __p.bb_pos) : (int)0; } }
+  public bool MutateTesthashs32Fnv1(int testhashs32_fnv1) { int o = __p.__offset(36); if (o != 0) { __p.bb.PutInt(o + __p.bb_pos, testhashs32_fnv1); return true; } else { return false; } }
+  public uint Testhashu32Fnv1 { get { int o = __p.__offset(38); return o != 0 ? __p.bb.GetUint(o + __p.bb_pos) : (uint)0; } }
+  public bool MutateTesthashu32Fnv1(uint testhashu32_fnv1) { int o = __p.__offset(38); if (o != 0) { __p.bb.PutUint(o + __p.bb_pos, testhashu32_fnv1); return true; } else { return false; } }
+  public long Testhashs64Fnv1 { get { int o = __p.__offset(40); return o != 0 ? __p.bb.GetLong(o + __p.bb_pos) : (long)0; } }
+  public bool MutateTesthashs64Fnv1(long testhashs64_fnv1) { int o = __p.__offset(40); if (o != 0) { __p.bb.PutLong(o + __p.bb_pos, testhashs64_fnv1); return true; } else { return false; } }
+  public ulong Testhashu64Fnv1 { get { int o = __p.__offset(42); return o != 0 ? __p.bb.GetUlong(o + __p.bb_pos) : (ulong)0; } }
+  public bool MutateTesthashu64Fnv1(ulong testhashu64_fnv1) { int o = __p.__offset(42); if (o != 0) { __p.bb.PutUlong(o + __p.bb_pos, testhashu64_fnv1); return true; } else { return false; } }
+  public int Testhashs32Fnv1a { get { int o = __p.__offset(44); return o != 0 ? __p.bb.GetInt(o + __p.bb_pos) : (int)0; } }
+  public bool MutateTesthashs32Fnv1a(int testhashs32_fnv1a) { int o = __p.__offset(44); if (o != 0) { __p.bb.PutInt(o + __p.bb_pos, testhashs32_fnv1a); return true; } else { return false; } }
+  public uint Testhashu32Fnv1a { get { int o = __p.__offset(46); return o != 0 ? __p.bb.GetUint(o + __p.bb_pos) : (uint)0; } }
+  public bool MutateTesthashu32Fnv1a(uint testhashu32_fnv1a) { int o = __p.__offset(46); if (o != 0) { __p.bb.PutUint(o + __p.bb_pos, testhashu32_fnv1a); return true; } else { return false; } }
+  public long Testhashs64Fnv1a { get { int o = __p.__offset(48); return o != 0 ? __p.bb.GetLong(o + __p.bb_pos) : (long)0; } }
+  public bool MutateTesthashs64Fnv1a(long testhashs64_fnv1a) { int o = __p.__offset(48); if (o != 0) { __p.bb.PutLong(o + __p.bb_pos, testhashs64_fnv1a); return true; } else { return false; } }
+  public ulong Testhashu64Fnv1a { get { int o = __p.__offset(50); return o != 0 ? __p.bb.GetUlong(o + __p.bb_pos) : (ulong)0; } }
+  public bool MutateTesthashu64Fnv1a(ulong testhashu64_fnv1a) { int o = __p.__offset(50); if (o != 0) { __p.bb.PutUlong(o + __p.bb_pos, testhashu64_fnv1a); return true; } else { return false; } }
+  public bool Testarrayofbools(int j) { int o = __p.__offset(52); return o != 0 ? 0!=__p.bb.Get(__p.__vector(o) + j * 1) : false; }
+  public int TestarrayofboolsLength { get { int o = __p.__offset(52); return o != 0 ? __p.__vector_len(o) : 0; } }
+  public ArraySegment<byte>? GetTestarrayofboolsBytes() { return __p.__vector_as_arraysegment(52); }
+  public bool MutateTestarrayofbools(int j, bool testarrayofbools) { int o = __p.__offset(52); if (o != 0) { __p.bb.Put(__p.__vector(o) + j * 1, (byte)(testarrayofbools ? 1 : 0)); return true; } else { return false; } }
+  public float Testf { get { int o = __p.__offset(54); return o != 0 ? __p.bb.GetFloat(o + __p.bb_pos) : (float)3.14159f; } }
+  public bool MutateTestf(float testf) { int o = __p.__offset(54); if (o != 0) { __p.bb.PutFloat(o + __p.bb_pos, testf); return true; } else { return false; } }
+  public float Testf2 { get { int o = __p.__offset(56); return o != 0 ? __p.bb.GetFloat(o + __p.bb_pos) : (float)3.0f; } }
+  public bool MutateTestf2(float testf2) { int o = __p.__offset(56); if (o != 0) { __p.bb.PutFloat(o + __p.bb_pos, testf2); return true; } else { return false; } }
+  public float Testf3 { get { int o = __p.__offset(58); return o != 0 ? __p.bb.GetFloat(o + __p.bb_pos) : (float)0.0f; } }
+  public bool MutateTestf3(float testf3) { int o = __p.__offset(58); if (o != 0) { __p.bb.PutFloat(o + __p.bb_pos, testf3); return true; } else { return false; } }
+  public string Testarrayofstring2(int j) { int o = __p.__offset(60); return o != 0 ? __p.__string(__p.__vector(o) + j * 4) : null; }
+  public int Testarrayofstring2Length { get { int o = __p.__offset(60); return o != 0 ? __p.__vector_len(o) : 0; } }
 
   public static void StartMonster(FlatBufferBuilder builder) { builder.StartObject(29); }
   public static void AddPos(FlatBufferBuilder builder, Offset<Vec3> posOffset) { builder.AddStruct(0, posOffset.Value, 0); }
@@ -129,6 +127,34 @@
     return new Offset<Monster>(o);
   }
   public static void FinishMonsterBuffer(FlatBufferBuilder builder, Offset<Monster> offset) { builder.Finish(offset.Value, "MONS"); }
+
+  public static VectorOffset CreateMySortedVectorOfTables(FlatBufferBuilder builder, Offset<Monster>[] offsets) {
+    Array.Sort(offsets, (Offset<Monster> o1, Offset<Monster> o2) => Table.CompareStrings(Table.__offset(10, o1.Value, builder.DataBuffer), Table.__offset(10, o2.Value, builder.DataBuffer), builder.DataBuffer));
+    return builder.CreateVectorOfTables(offsets);
+  }
+
+  public static Monster? LookupByKey(VectorOffset vectorOffset, string key, ByteBuffer bb) {
+    byte[] byteKey = System.Text.Encoding.UTF8.GetBytes(key);
+    int vectorLocation = bb.Length - vectorOffset.Value;
+    int span = bb.GetInt(vectorLocation);
+    int start = 0;
+    vectorLocation += 4;
+    while (span != 0) {
+      int middle = span / 2;
+      int tableOffset = Table.__indirect(vectorLocation + 4 * (start + middle), bb);
+      int comp = Table.CompareStrings(Table.__offset(10, bb.Length - tableOffset, bb), byteKey, bb);
+      if (comp > 0) {
+        span = middle;
+      } else if (comp < 0) {
+        middle++;
+        start += middle;
+        span -= middle;
+      } else {
+        return new Monster().__assign(tableOffset, bb);
+      }
+    }
+    return null;
+  }
 };
 
 
diff --git a/tests/MyGame/Example/Monster.go b/tests/MyGame/Example/Monster.go
index 0c42f45..ba3ae0f 100644
--- a/tests/MyGame/Example/Monster.go
+++ b/tests/MyGame/Example/Monster.go
@@ -5,6 +5,7 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 /// an example documentation comment: monster object
 type Monster struct {
 	_tab flatbuffers.Table
@@ -13,7 +14,7 @@
 func GetRootAsMonster(buf []byte, offset flatbuffers.UOffsetT) *Monster {
 	n := flatbuffers.GetUOffsetT(buf[offset:])
 	x := &Monster{}
-	x.Init(buf, n + offset)
+	x.Init(buf, n+offset)
 	return x
 }
 
@@ -22,6 +23,10 @@
 	rcv._tab.Pos = i
 }
 
+func (rcv *Monster) Table() flatbuffers.Table {
+	return rcv._tab
+}
+
 func (rcv *Monster) Pos(obj *Vec3) *Vec3 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(4))
 	if o != 0 {
@@ -43,6 +48,10 @@
 	return 150
 }
 
+func (rcv *Monster) MutateMana(n int16) bool {
+	return rcv._tab.MutateInt16Slot(6, n)
+}
+
 func (rcv *Monster) Hp() int16 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(8))
 	if o != 0 {
@@ -51,6 +60,10 @@
 	return 100
 }
 
+func (rcv *Monster) MutateHp(n int16) bool {
+	return rcv._tab.MutateInt16Slot(8, n)
+}
+
 func (rcv *Monster) Name() []byte {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(10))
 	if o != 0 {
@@ -63,7 +76,7 @@
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(14))
 	if o != 0 {
 		a := rcv._tab.Vector(o)
-		return rcv._tab.GetByte(a + flatbuffers.UOffsetT(j * 1))
+		return rcv._tab.GetByte(a + flatbuffers.UOffsetT(j*1))
 	}
 	return 0
 }
@@ -92,6 +105,10 @@
 	return 8
 }
 
+func (rcv *Monster) MutateColor(n int8) bool {
+	return rcv._tab.MutateInt8Slot(16, n)
+}
+
 func (rcv *Monster) TestType() byte {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(18))
 	if o != 0 {
@@ -100,6 +117,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTestType(n byte) bool {
+	return rcv._tab.MutateByteSlot(18, n)
+}
+
 func (rcv *Monster) Test(obj *flatbuffers.Table) bool {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(20))
 	if o != 0 {
@@ -114,9 +135,6 @@
 	if o != 0 {
 		x := rcv._tab.Vector(o)
 		x += flatbuffers.UOffsetT(j) * 4
-	if obj == nil {
-		obj = new(Test)
-	}
 		obj.Init(rcv._tab.Bytes, x)
 		return true
 	}
@@ -135,7 +153,7 @@
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(24))
 	if o != 0 {
 		a := rcv._tab.Vector(o)
-		return rcv._tab.ByteVector(a + flatbuffers.UOffsetT(j * 4))
+		return rcv._tab.ByteVector(a + flatbuffers.UOffsetT(j*4))
 	}
 	return nil
 }
@@ -156,9 +174,6 @@
 		x := rcv._tab.Vector(o)
 		x += flatbuffers.UOffsetT(j) * 4
 		x = rcv._tab.Indirect(x)
-	if obj == nil {
-		obj = new(Monster)
-	}
 		obj.Init(rcv._tab.Bytes, x)
 		return true
 	}
@@ -173,6 +188,8 @@
 	return 0
 }
 
+/// an example documentation comment: this will end up in the generated code
+/// multiline too
 func (rcv *Monster) Enemy(obj *Monster) *Monster {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(28))
 	if o != 0 {
@@ -190,7 +207,7 @@
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(30))
 	if o != 0 {
 		a := rcv._tab.Vector(o)
-		return rcv._tab.GetByte(a + flatbuffers.UOffsetT(j * 1))
+		return rcv._tab.GetByte(a + flatbuffers.UOffsetT(j*1))
 	}
 	return 0
 }
@@ -232,6 +249,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTestbool(n byte) bool {
+	return rcv._tab.MutateByteSlot(34, n)
+}
+
 func (rcv *Monster) Testhashs32Fnv1() int32 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(36))
 	if o != 0 {
@@ -240,6 +261,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashs32Fnv1(n int32) bool {
+	return rcv._tab.MutateInt32Slot(36, n)
+}
+
 func (rcv *Monster) Testhashu32Fnv1() uint32 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(38))
 	if o != 0 {
@@ -248,6 +273,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashu32Fnv1(n uint32) bool {
+	return rcv._tab.MutateUint32Slot(38, n)
+}
+
 func (rcv *Monster) Testhashs64Fnv1() int64 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(40))
 	if o != 0 {
@@ -256,6 +285,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashs64Fnv1(n int64) bool {
+	return rcv._tab.MutateInt64Slot(40, n)
+}
+
 func (rcv *Monster) Testhashu64Fnv1() uint64 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(42))
 	if o != 0 {
@@ -264,6 +297,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashu64Fnv1(n uint64) bool {
+	return rcv._tab.MutateUint64Slot(42, n)
+}
+
 func (rcv *Monster) Testhashs32Fnv1a() int32 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(44))
 	if o != 0 {
@@ -272,6 +309,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashs32Fnv1a(n int32) bool {
+	return rcv._tab.MutateInt32Slot(44, n)
+}
+
 func (rcv *Monster) Testhashu32Fnv1a() uint32 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(46))
 	if o != 0 {
@@ -280,6 +321,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashu32Fnv1a(n uint32) bool {
+	return rcv._tab.MutateUint32Slot(46, n)
+}
+
 func (rcv *Monster) Testhashs64Fnv1a() int64 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(48))
 	if o != 0 {
@@ -288,6 +333,10 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashs64Fnv1a(n int64) bool {
+	return rcv._tab.MutateInt64Slot(48, n)
+}
+
 func (rcv *Monster) Testhashu64Fnv1a() uint64 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(50))
 	if o != 0 {
@@ -296,11 +345,15 @@
 	return 0
 }
 
+func (rcv *Monster) MutateTesthashu64Fnv1a(n uint64) bool {
+	return rcv._tab.MutateUint64Slot(50, n)
+}
+
 func (rcv *Monster) Testarrayofbools(j int) byte {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(52))
 	if o != 0 {
 		a := rcv._tab.Vector(o)
-		return rcv._tab.GetByte(a + flatbuffers.UOffsetT(j * 1))
+		return rcv._tab.GetByte(a + flatbuffers.UOffsetT(j*1))
 	}
 	return 0
 }
@@ -321,6 +374,10 @@
 	return 3.14159
 }
 
+func (rcv *Monster) MutateTestf(n float32) bool {
+	return rcv._tab.MutateFloat32Slot(54, n)
+}
+
 func (rcv *Monster) Testf2() float32 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(56))
 	if o != 0 {
@@ -329,6 +386,10 @@
 	return 3.0
 }
 
+func (rcv *Monster) MutateTestf2(n float32) bool {
+	return rcv._tab.MutateFloat32Slot(56, n)
+}
+
 func (rcv *Monster) Testf3() float32 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(58))
 	if o != 0 {
@@ -337,11 +398,15 @@
 	return 0.0
 }
 
+func (rcv *Monster) MutateTestf3(n float32) bool {
+	return rcv._tab.MutateFloat32Slot(58, n)
+}
+
 func (rcv *Monster) Testarrayofstring2(j int) []byte {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(60))
 	if o != 0 {
 		a := rcv._tab.Vector(o)
-		return rcv._tab.ByteVector(a + flatbuffers.UOffsetT(j * 4))
+		return rcv._tab.ByteVector(a + flatbuffers.UOffsetT(j*4))
 	}
 	return nil
 }
@@ -354,47 +419,114 @@
 	return 0
 }
 
-func MonsterStart(builder *flatbuffers.Builder) { builder.StartObject(29) }
-func MonsterAddPos(builder *flatbuffers.Builder, pos flatbuffers.UOffsetT) { builder.PrependStructSlot(0, flatbuffers.UOffsetT(pos), 0) }
-func MonsterAddMana(builder *flatbuffers.Builder, mana int16) { builder.PrependInt16Slot(1, mana, 150) }
-func MonsterAddHp(builder *flatbuffers.Builder, hp int16) { builder.PrependInt16Slot(2, hp, 100) }
-func MonsterAddName(builder *flatbuffers.Builder, name flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(3, flatbuffers.UOffsetT(name), 0) }
-func MonsterAddInventory(builder *flatbuffers.Builder, inventory flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(5, flatbuffers.UOffsetT(inventory), 0) }
-func MonsterStartInventoryVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT { return builder.StartVector(1, numElems, 1)
+func MonsterStart(builder *flatbuffers.Builder) {
+	builder.StartObject(29)
 }
-func MonsterAddColor(builder *flatbuffers.Builder, color int8) { builder.PrependInt8Slot(6, color, 8) }
-func MonsterAddTestType(builder *flatbuffers.Builder, testType byte) { builder.PrependByteSlot(7, testType, 0) }
-func MonsterAddTest(builder *flatbuffers.Builder, test flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(8, flatbuffers.UOffsetT(test), 0) }
-func MonsterAddTest4(builder *flatbuffers.Builder, test4 flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(9, flatbuffers.UOffsetT(test4), 0) }
-func MonsterStartTest4Vector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT { return builder.StartVector(4, numElems, 2)
+func MonsterAddPos(builder *flatbuffers.Builder, pos flatbuffers.UOffsetT) {
+	builder.PrependStructSlot(0, flatbuffers.UOffsetT(pos), 0)
 }
-func MonsterAddTestarrayofstring(builder *flatbuffers.Builder, testarrayofstring flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(10, flatbuffers.UOffsetT(testarrayofstring), 0) }
-func MonsterStartTestarrayofstringVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT { return builder.StartVector(4, numElems, 4)
+func MonsterAddMana(builder *flatbuffers.Builder, mana int16) {
+	builder.PrependInt16Slot(1, mana, 150)
 }
-func MonsterAddTestarrayoftables(builder *flatbuffers.Builder, testarrayoftables flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(11, flatbuffers.UOffsetT(testarrayoftables), 0) }
-func MonsterStartTestarrayoftablesVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT { return builder.StartVector(4, numElems, 4)
+func MonsterAddHp(builder *flatbuffers.Builder, hp int16) {
+	builder.PrependInt16Slot(2, hp, 100)
 }
-func MonsterAddEnemy(builder *flatbuffers.Builder, enemy flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(12, flatbuffers.UOffsetT(enemy), 0) }
-func MonsterAddTestnestedflatbuffer(builder *flatbuffers.Builder, testnestedflatbuffer flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(13, flatbuffers.UOffsetT(testnestedflatbuffer), 0) }
-func MonsterStartTestnestedflatbufferVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT { return builder.StartVector(1, numElems, 1)
+func MonsterAddName(builder *flatbuffers.Builder, name flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(3, flatbuffers.UOffsetT(name), 0)
 }
-func MonsterAddTestempty(builder *flatbuffers.Builder, testempty flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(14, flatbuffers.UOffsetT(testempty), 0) }
-func MonsterAddTestbool(builder *flatbuffers.Builder, testbool byte) { builder.PrependByteSlot(15, testbool, 0) }
-func MonsterAddTesthashs32Fnv1(builder *flatbuffers.Builder, testhashs32Fnv1 int32) { builder.PrependInt32Slot(16, testhashs32Fnv1, 0) }
-func MonsterAddTesthashu32Fnv1(builder *flatbuffers.Builder, testhashu32Fnv1 uint32) { builder.PrependUint32Slot(17, testhashu32Fnv1, 0) }
-func MonsterAddTesthashs64Fnv1(builder *flatbuffers.Builder, testhashs64Fnv1 int64) { builder.PrependInt64Slot(18, testhashs64Fnv1, 0) }
-func MonsterAddTesthashu64Fnv1(builder *flatbuffers.Builder, testhashu64Fnv1 uint64) { builder.PrependUint64Slot(19, testhashu64Fnv1, 0) }
-func MonsterAddTesthashs32Fnv1a(builder *flatbuffers.Builder, testhashs32Fnv1a int32) { builder.PrependInt32Slot(20, testhashs32Fnv1a, 0) }
-func MonsterAddTesthashu32Fnv1a(builder *flatbuffers.Builder, testhashu32Fnv1a uint32) { builder.PrependUint32Slot(21, testhashu32Fnv1a, 0) }
-func MonsterAddTesthashs64Fnv1a(builder *flatbuffers.Builder, testhashs64Fnv1a int64) { builder.PrependInt64Slot(22, testhashs64Fnv1a, 0) }
-func MonsterAddTesthashu64Fnv1a(builder *flatbuffers.Builder, testhashu64Fnv1a uint64) { builder.PrependUint64Slot(23, testhashu64Fnv1a, 0) }
-func MonsterAddTestarrayofbools(builder *flatbuffers.Builder, testarrayofbools flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(24, flatbuffers.UOffsetT(testarrayofbools), 0) }
-func MonsterStartTestarrayofboolsVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT { return builder.StartVector(1, numElems, 1)
+func MonsterAddInventory(builder *flatbuffers.Builder, inventory flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(5, flatbuffers.UOffsetT(inventory), 0)
 }
-func MonsterAddTestf(builder *flatbuffers.Builder, testf float32) { builder.PrependFloat32Slot(25, testf, 3.14159) }
-func MonsterAddTestf2(builder *flatbuffers.Builder, testf2 float32) { builder.PrependFloat32Slot(26, testf2, 3.0) }
-func MonsterAddTestf3(builder *flatbuffers.Builder, testf3 float32) { builder.PrependFloat32Slot(27, testf3, 0.0) }
-func MonsterAddTestarrayofstring2(builder *flatbuffers.Builder, testarrayofstring2 flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(28, flatbuffers.UOffsetT(testarrayofstring2), 0) }
-func MonsterStartTestarrayofstring2Vector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT { return builder.StartVector(4, numElems, 4)
+func MonsterStartInventoryVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT {
+	return builder.StartVector(1, numElems, 1)
 }
-func MonsterEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func MonsterAddColor(builder *flatbuffers.Builder, color int8) {
+	builder.PrependInt8Slot(6, color, 8)
+}
+func MonsterAddTestType(builder *flatbuffers.Builder, testType byte) {
+	builder.PrependByteSlot(7, testType, 0)
+}
+func MonsterAddTest(builder *flatbuffers.Builder, test flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(8, flatbuffers.UOffsetT(test), 0)
+}
+func MonsterAddTest4(builder *flatbuffers.Builder, test4 flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(9, flatbuffers.UOffsetT(test4), 0)
+}
+func MonsterStartTest4Vector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT {
+	return builder.StartVector(4, numElems, 2)
+}
+func MonsterAddTestarrayofstring(builder *flatbuffers.Builder, testarrayofstring flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(10, flatbuffers.UOffsetT(testarrayofstring), 0)
+}
+func MonsterStartTestarrayofstringVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT {
+	return builder.StartVector(4, numElems, 4)
+}
+func MonsterAddTestarrayoftables(builder *flatbuffers.Builder, testarrayoftables flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(11, flatbuffers.UOffsetT(testarrayoftables), 0)
+}
+func MonsterStartTestarrayoftablesVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT {
+	return builder.StartVector(4, numElems, 4)
+}
+func MonsterAddEnemy(builder *flatbuffers.Builder, enemy flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(12, flatbuffers.UOffsetT(enemy), 0)
+}
+func MonsterAddTestnestedflatbuffer(builder *flatbuffers.Builder, testnestedflatbuffer flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(13, flatbuffers.UOffsetT(testnestedflatbuffer), 0)
+}
+func MonsterStartTestnestedflatbufferVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT {
+	return builder.StartVector(1, numElems, 1)
+}
+func MonsterAddTestempty(builder *flatbuffers.Builder, testempty flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(14, flatbuffers.UOffsetT(testempty), 0)
+}
+func MonsterAddTestbool(builder *flatbuffers.Builder, testbool byte) {
+	builder.PrependByteSlot(15, testbool, 0)
+}
+func MonsterAddTesthashs32Fnv1(builder *flatbuffers.Builder, testhashs32Fnv1 int32) {
+	builder.PrependInt32Slot(16, testhashs32Fnv1, 0)
+}
+func MonsterAddTesthashu32Fnv1(builder *flatbuffers.Builder, testhashu32Fnv1 uint32) {
+	builder.PrependUint32Slot(17, testhashu32Fnv1, 0)
+}
+func MonsterAddTesthashs64Fnv1(builder *flatbuffers.Builder, testhashs64Fnv1 int64) {
+	builder.PrependInt64Slot(18, testhashs64Fnv1, 0)
+}
+func MonsterAddTesthashu64Fnv1(builder *flatbuffers.Builder, testhashu64Fnv1 uint64) {
+	builder.PrependUint64Slot(19, testhashu64Fnv1, 0)
+}
+func MonsterAddTesthashs32Fnv1a(builder *flatbuffers.Builder, testhashs32Fnv1a int32) {
+	builder.PrependInt32Slot(20, testhashs32Fnv1a, 0)
+}
+func MonsterAddTesthashu32Fnv1a(builder *flatbuffers.Builder, testhashu32Fnv1a uint32) {
+	builder.PrependUint32Slot(21, testhashu32Fnv1a, 0)
+}
+func MonsterAddTesthashs64Fnv1a(builder *flatbuffers.Builder, testhashs64Fnv1a int64) {
+	builder.PrependInt64Slot(22, testhashs64Fnv1a, 0)
+}
+func MonsterAddTesthashu64Fnv1a(builder *flatbuffers.Builder, testhashu64Fnv1a uint64) {
+	builder.PrependUint64Slot(23, testhashu64Fnv1a, 0)
+}
+func MonsterAddTestarrayofbools(builder *flatbuffers.Builder, testarrayofbools flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(24, flatbuffers.UOffsetT(testarrayofbools), 0)
+}
+func MonsterStartTestarrayofboolsVector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT {
+	return builder.StartVector(1, numElems, 1)
+}
+func MonsterAddTestf(builder *flatbuffers.Builder, testf float32) {
+	builder.PrependFloat32Slot(25, testf, 3.14159)
+}
+func MonsterAddTestf2(builder *flatbuffers.Builder, testf2 float32) {
+	builder.PrependFloat32Slot(26, testf2, 3.0)
+}
+func MonsterAddTestf3(builder *flatbuffers.Builder, testf3 float32) {
+	builder.PrependFloat32Slot(27, testf3, 0.0)
+}
+func MonsterAddTestarrayofstring2(builder *flatbuffers.Builder, testarrayofstring2 flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(28, flatbuffers.UOffsetT(testarrayofstring2), 0)
+}
+func MonsterStartTestarrayofstring2Vector(builder *flatbuffers.Builder, numElems int) flatbuffers.UOffsetT {
+	return builder.StartVector(4, numElems, 4)
+}
+func MonsterEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/MyGame/Example/Monster.java b/tests/MyGame/Example/Monster.java
index dc27f84..10a9aa4 100644
--- a/tests/MyGame/Example/Monster.java
+++ b/tests/MyGame/Example/Monster.java
@@ -13,12 +13,13 @@
  */
 public final class Monster extends Table {
   public static Monster getRootAsMonster(ByteBuffer _bb) { return getRootAsMonster(_bb, new Monster()); }
-  public static Monster getRootAsMonster(ByteBuffer _bb, Monster obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public static Monster getRootAsMonster(ByteBuffer _bb, Monster obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
   public static boolean MonsterBufferHasIdentifier(ByteBuffer _bb) { return __has_identifier(_bb, "MONS"); }
-  public Monster __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public Monster __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public Vec3 pos() { return pos(new Vec3()); }
-  public Vec3 pos(Vec3 obj) { int o = __offset(4); return o != 0 ? obj.__init(o + bb_pos, bb) : null; }
+  public Vec3 pos(Vec3 obj) { int o = __offset(4); return o != 0 ? obj.__assign(o + bb_pos, bb) : null; }
   public short mana() { int o = __offset(6); return o != 0 ? bb.getShort(o + bb_pos) : 150; }
   public boolean mutateMana(short mana) { int o = __offset(6); if (o != 0) { bb.putShort(o + bb_pos, mana); return true; } else { return false; } }
   public short hp() { int o = __offset(8); return o != 0 ? bb.getShort(o + bb_pos) : 100; }
@@ -35,7 +36,7 @@
   public boolean mutateTestType(byte test_type) { int o = __offset(18); if (o != 0) { bb.put(o + bb_pos, test_type); return true; } else { return false; } }
   public Table test(Table obj) { int o = __offset(20); return o != 0 ? __union(obj, o) : null; }
   public Test test4(int j) { return test4(new Test(), j); }
-  public Test test4(Test obj, int j) { int o = __offset(22); return o != 0 ? obj.__init(__vector(o) + j * 4, bb) : null; }
+  public Test test4(Test obj, int j) { int o = __offset(22); return o != 0 ? obj.__assign(__vector(o) + j * 4, bb) : null; }
   public int test4Length() { int o = __offset(22); return o != 0 ? __vector_len(o) : 0; }
   public String testarrayofstring(int j) { int o = __offset(24); return o != 0 ? __string(__vector(o) + j * 4) : null; }
   public int testarrayofstringLength() { int o = __offset(24); return o != 0 ? __vector_len(o) : 0; }
@@ -44,35 +45,35 @@
    * multiline too
    */
   public Monster testarrayoftables(int j) { return testarrayoftables(new Monster(), j); }
-  public Monster testarrayoftables(Monster obj, int j) { int o = __offset(26); return o != 0 ? obj.__init(__indirect(__vector(o) + j * 4), bb) : null; }
+  public Monster testarrayoftables(Monster obj, int j) { int o = __offset(26); return o != 0 ? obj.__assign(__indirect(__vector(o) + j * 4), bb) : null; }
   public int testarrayoftablesLength() { int o = __offset(26); return o != 0 ? __vector_len(o) : 0; }
   public Monster enemy() { return enemy(new Monster()); }
-  public Monster enemy(Monster obj) { int o = __offset(28); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
+  public Monster enemy(Monster obj) { int o = __offset(28); return o != 0 ? obj.__assign(__indirect(o + bb_pos), bb) : null; }
   public int testnestedflatbuffer(int j) { int o = __offset(30); return o != 0 ? bb.get(__vector(o) + j * 1) & 0xFF : 0; }
   public int testnestedflatbufferLength() { int o = __offset(30); return o != 0 ? __vector_len(o) : 0; }
   public ByteBuffer testnestedflatbufferAsByteBuffer() { return __vector_as_bytebuffer(30, 1); }
   public Monster testnestedflatbufferAsMonster() { return testnestedflatbufferAsMonster(new Monster()); }
-  public Monster testnestedflatbufferAsMonster(Monster obj) { int o = __offset(30); return o != 0 ? obj.__init(__indirect(__vector(o)), bb) : null; }
+  public Monster testnestedflatbufferAsMonster(Monster obj) { int o = __offset(30); return o != 0 ? obj.__assign(__indirect(__vector(o)), bb) : null; }
   public boolean mutateTestnestedflatbuffer(int j, int testnestedflatbuffer) { int o = __offset(30); if (o != 0) { bb.put(__vector(o) + j * 1, (byte)testnestedflatbuffer); return true; } else { return false; } }
   public Stat testempty() { return testempty(new Stat()); }
-  public Stat testempty(Stat obj) { int o = __offset(32); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
+  public Stat testempty(Stat obj) { int o = __offset(32); return o != 0 ? obj.__assign(__indirect(o + bb_pos), bb) : null; }
   public boolean testbool() { int o = __offset(34); return o != 0 ? 0!=bb.get(o + bb_pos) : false; }
   public boolean mutateTestbool(boolean testbool) { int o = __offset(34); if (o != 0) { bb.put(o + bb_pos, (byte)(testbool ? 1 : 0)); return true; } else { return false; } }
   public int testhashs32Fnv1() { int o = __offset(36); return o != 0 ? bb.getInt(o + bb_pos) : 0; }
   public boolean mutateTesthashs32Fnv1(int testhashs32_fnv1) { int o = __offset(36); if (o != 0) { bb.putInt(o + bb_pos, testhashs32_fnv1); return true; } else { return false; } }
-  public long testhashu32Fnv1() { int o = __offset(38); return o != 0 ? (long)bb.getInt(o + bb_pos) & 0xFFFFFFFFL : 0; }
+  public long testhashu32Fnv1() { int o = __offset(38); return o != 0 ? (long)bb.getInt(o + bb_pos) & 0xFFFFFFFFL : 0L; }
   public boolean mutateTesthashu32Fnv1(long testhashu32_fnv1) { int o = __offset(38); if (o != 0) { bb.putInt(o + bb_pos, (int)testhashu32_fnv1); return true; } else { return false; } }
-  public long testhashs64Fnv1() { int o = __offset(40); return o != 0 ? bb.getLong(o + bb_pos) : 0; }
+  public long testhashs64Fnv1() { int o = __offset(40); return o != 0 ? bb.getLong(o + bb_pos) : 0L; }
   public boolean mutateTesthashs64Fnv1(long testhashs64_fnv1) { int o = __offset(40); if (o != 0) { bb.putLong(o + bb_pos, testhashs64_fnv1); return true; } else { return false; } }
-  public long testhashu64Fnv1() { int o = __offset(42); return o != 0 ? bb.getLong(o + bb_pos) : 0; }
+  public long testhashu64Fnv1() { int o = __offset(42); return o != 0 ? bb.getLong(o + bb_pos) : 0L; }
   public boolean mutateTesthashu64Fnv1(long testhashu64_fnv1) { int o = __offset(42); if (o != 0) { bb.putLong(o + bb_pos, testhashu64_fnv1); return true; } else { return false; } }
   public int testhashs32Fnv1a() { int o = __offset(44); return o != 0 ? bb.getInt(o + bb_pos) : 0; }
   public boolean mutateTesthashs32Fnv1a(int testhashs32_fnv1a) { int o = __offset(44); if (o != 0) { bb.putInt(o + bb_pos, testhashs32_fnv1a); return true; } else { return false; } }
-  public long testhashu32Fnv1a() { int o = __offset(46); return o != 0 ? (long)bb.getInt(o + bb_pos) & 0xFFFFFFFFL : 0; }
+  public long testhashu32Fnv1a() { int o = __offset(46); return o != 0 ? (long)bb.getInt(o + bb_pos) & 0xFFFFFFFFL : 0L; }
   public boolean mutateTesthashu32Fnv1a(long testhashu32_fnv1a) { int o = __offset(46); if (o != 0) { bb.putInt(o + bb_pos, (int)testhashu32_fnv1a); return true; } else { return false; } }
-  public long testhashs64Fnv1a() { int o = __offset(48); return o != 0 ? bb.getLong(o + bb_pos) : 0; }
+  public long testhashs64Fnv1a() { int o = __offset(48); return o != 0 ? bb.getLong(o + bb_pos) : 0L; }
   public boolean mutateTesthashs64Fnv1a(long testhashs64_fnv1a) { int o = __offset(48); if (o != 0) { bb.putLong(o + bb_pos, testhashs64_fnv1a); return true; } else { return false; } }
-  public long testhashu64Fnv1a() { int o = __offset(50); return o != 0 ? bb.getLong(o + bb_pos) : 0; }
+  public long testhashu64Fnv1a() { int o = __offset(50); return o != 0 ? bb.getLong(o + bb_pos) : 0L; }
   public boolean mutateTesthashu64Fnv1a(long testhashu64_fnv1a) { int o = __offset(50); if (o != 0) { bb.putLong(o + bb_pos, testhashu64_fnv1a); return true; } else { return false; } }
   public boolean testarrayofbools(int j) { int o = __offset(52); return o != 0 ? 0!=bb.get(__vector(o) + j * 1) : false; }
   public int testarrayofboolsLength() { int o = __offset(52); return o != 0 ? __vector_len(o) : 0; }
@@ -113,13 +114,13 @@
   public static void addTestempty(FlatBufferBuilder builder, int testemptyOffset) { builder.addOffset(14, testemptyOffset, 0); }
   public static void addTestbool(FlatBufferBuilder builder, boolean testbool) { builder.addBoolean(15, testbool, false); }
   public static void addTesthashs32Fnv1(FlatBufferBuilder builder, int testhashs32Fnv1) { builder.addInt(16, testhashs32Fnv1, 0); }
-  public static void addTesthashu32Fnv1(FlatBufferBuilder builder, long testhashu32Fnv1) { builder.addInt(17, (int)testhashu32Fnv1, 0); }
-  public static void addTesthashs64Fnv1(FlatBufferBuilder builder, long testhashs64Fnv1) { builder.addLong(18, testhashs64Fnv1, 0); }
-  public static void addTesthashu64Fnv1(FlatBufferBuilder builder, long testhashu64Fnv1) { builder.addLong(19, testhashu64Fnv1, 0); }
+  public static void addTesthashu32Fnv1(FlatBufferBuilder builder, long testhashu32Fnv1) { builder.addInt(17, (int)testhashu32Fnv1, (int)0L); }
+  public static void addTesthashs64Fnv1(FlatBufferBuilder builder, long testhashs64Fnv1) { builder.addLong(18, testhashs64Fnv1, 0L); }
+  public static void addTesthashu64Fnv1(FlatBufferBuilder builder, long testhashu64Fnv1) { builder.addLong(19, testhashu64Fnv1, 0L); }
   public static void addTesthashs32Fnv1a(FlatBufferBuilder builder, int testhashs32Fnv1a) { builder.addInt(20, testhashs32Fnv1a, 0); }
-  public static void addTesthashu32Fnv1a(FlatBufferBuilder builder, long testhashu32Fnv1a) { builder.addInt(21, (int)testhashu32Fnv1a, 0); }
-  public static void addTesthashs64Fnv1a(FlatBufferBuilder builder, long testhashs64Fnv1a) { builder.addLong(22, testhashs64Fnv1a, 0); }
-  public static void addTesthashu64Fnv1a(FlatBufferBuilder builder, long testhashu64Fnv1a) { builder.addLong(23, testhashu64Fnv1a, 0); }
+  public static void addTesthashu32Fnv1a(FlatBufferBuilder builder, long testhashu32Fnv1a) { builder.addInt(21, (int)testhashu32Fnv1a, (int)0L); }
+  public static void addTesthashs64Fnv1a(FlatBufferBuilder builder, long testhashs64Fnv1a) { builder.addLong(22, testhashs64Fnv1a, 0L); }
+  public static void addTesthashu64Fnv1a(FlatBufferBuilder builder, long testhashu64Fnv1a) { builder.addLong(23, testhashu64Fnv1a, 0L); }
   public static void addTestarrayofbools(FlatBufferBuilder builder, int testarrayofboolsOffset) { builder.addOffset(24, testarrayofboolsOffset, 0); }
   public static int createTestarrayofboolsVector(FlatBufferBuilder builder, boolean[] data) { builder.startVector(1, data.length, 1); for (int i = data.length - 1; i >= 0; i--) builder.addBoolean(data[i]); return builder.endVector(); }
   public static void startTestarrayofboolsVector(FlatBufferBuilder builder, int numElems) { builder.startVector(1, numElems, 1); }
@@ -135,5 +136,31 @@
     return o;
   }
   public static void finishMonsterBuffer(FlatBufferBuilder builder, int offset) { builder.finish(offset, "MONS"); }
+
+  @Override
+  protected int keysCompare(Integer o1, Integer o2, ByteBuffer _bb) { return compareStrings(__offset(10, o1, _bb), __offset(10, o2, _bb), _bb); }
+
+  public static Monster lookupByKey(int vectorOffset, String key, ByteBuffer bb) {
+    byte[] byteKey = key.getBytes(Table.UTF8_CHARSET.get());
+    int vectorLocation = bb.array().length - vectorOffset;
+    int span = bb.getInt(vectorLocation);
+    int start = 0;
+    vectorLocation += 4;
+    while (span != 0) {
+      int middle = span / 2;
+      int tableOffset = __indirect(vectorLocation + 4 * (start + middle), bb);
+      int comp = compareStrings(__offset(10, bb.array().length - tableOffset, bb), byteKey, bb);
+      if (comp > 0) {
+        span = middle;
+      } else if (comp < 0) {
+        middle++;
+        start += middle;
+        span -= middle;
+      } else {
+        return new Monster().__assign(tableOffset, bb);
+      }
+    }
+    return null;
+  }
 }
 
diff --git a/tests/MyGame/Example/Monster.py b/tests/MyGame/Example/Monster.py
index 9d2909e..a7a7836 100644
--- a/tests/MyGame/Example/Monster.py
+++ b/tests/MyGame/Example/Monster.py
@@ -15,7 +15,6 @@
         x.Init(buf, n + offset)
         return x
 
-
     # Monster
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/MyGame/Example/MonsterStorage_grpc.go b/tests/MyGame/Example/MonsterStorage_grpc.go
new file mode 100644
index 0000000..8aac5c2
--- /dev/null
+++ b/tests/MyGame/Example/MonsterStorage_grpc.go
@@ -0,0 +1,106 @@
+//Generated by gRPC Go plugin
+//If you make any local changes, they will be lost
+//source: monster_test
+
+package Example
+
+import "github.com/google/flatbuffers/go"
+
+import (
+  context "golang.org/x/net/context"
+  grpc "google.golang.org/grpc"
+)
+
+// Client API for MonsterStorage service
+type MonsterStorageClient interface{
+  Store(ctx context.Context, in *flatbuffers.Builder, 
+  	opts... grpc.CallOption) (* Stat, error)  
+  Retrieve(ctx context.Context, in *flatbuffers.Builder, 
+  	opts... grpc.CallOption) (* Monster, error)  
+}
+
+type monsterStorageClient struct {
+  cc *grpc.ClientConn
+}
+
+func NewMonsterStorageClient(cc *grpc.ClientConn) MonsterStorageClient {
+  return &monsterStorageClient{cc}
+}
+
+func (c *monsterStorageClient) Store(ctx context.Context, in *flatbuffers.Builder, 
+	opts... grpc.CallOption) (* Stat, error) {
+  out := new(Stat)
+  err := grpc.Invoke(ctx, "/Example.MonsterStorage/Store", in, out, c.cc, opts...)
+  if err != nil { return nil, err }
+  return out, nil
+}
+
+func (c *monsterStorageClient) Retrieve(ctx context.Context, in *flatbuffers.Builder, 
+	opts... grpc.CallOption) (* Monster, error) {
+  out := new(Monster)
+  err := grpc.Invoke(ctx, "/Example.MonsterStorage/Retrieve", in, out, c.cc, opts...)
+  if err != nil { return nil, err }
+  return out, nil
+}
+
+// Server API for MonsterStorage service
+type MonsterStorageServer interface {
+  Store(context.Context, *Monster) (*flatbuffers.Builder, error)  
+  Retrieve(context.Context, *Stat) (*flatbuffers.Builder, error)  
+}
+
+func RegisterMonsterStorageServer(s *grpc.Server, srv MonsterStorageServer) {
+  s.RegisterService(&_MonsterStorage_serviceDesc, srv)
+}
+
+func _MonsterStorage_Store_Handler(srv interface{}, ctx context.Context,
+	dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+  in := new(Monster)
+  if err := dec(in); err != nil { return nil, err }
+  if interceptor == nil { return srv.(MonsterStorageServer).Store(ctx, in) }
+  info := &grpc.UnaryServerInfo{
+    Server: srv,
+    FullMethod: "/Example.MonsterStorage/Store",
+  }
+  
+  handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+    return srv.(MonsterStorageServer).Store(ctx, req.(* Monster))
+  }
+  return interceptor(ctx, in, info, handler)
+}
+
+
+func _MonsterStorage_Retrieve_Handler(srv interface{}, ctx context.Context,
+	dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+  in := new(Stat)
+  if err := dec(in); err != nil { return nil, err }
+  if interceptor == nil { return srv.(MonsterStorageServer).Retrieve(ctx, in) }
+  info := &grpc.UnaryServerInfo{
+    Server: srv,
+    FullMethod: "/Example.MonsterStorage/Retrieve",
+  }
+  
+  handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+    return srv.(MonsterStorageServer).Retrieve(ctx, req.(* Stat))
+  }
+  return interceptor(ctx, in, info, handler)
+}
+
+
+var _MonsterStorage_serviceDesc = grpc.ServiceDesc{
+  ServiceName: "Example.MonsterStorage",
+  HandlerType: (*MonsterStorageServer)(nil),
+  Methods: []grpc.MethodDesc{
+    {
+      MethodName: "Store",
+      Handler: _MonsterStorage_Store_Handler, 
+    },
+    {
+      MethodName: "Retrieve",
+      Handler: _MonsterStorage_Retrieve_Handler, 
+    },
+  },
+  Streams: []grpc.StreamDesc{
+  },
+}
+
diff --git a/tests/MyGame/Example/Stat.cs b/tests/MyGame/Example/Stat.cs
index 30eaee5..0fb5bd0 100644
--- a/tests/MyGame/Example/Stat.cs
+++ b/tests/MyGame/Example/Stat.cs
@@ -6,17 +6,21 @@
 using System;
 using FlatBuffers;
 
-public sealed class Stat : Table {
+public struct Stat : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static Stat GetRootAsStat(ByteBuffer _bb) { return GetRootAsStat(_bb, new Stat()); }
-  public static Stat GetRootAsStat(ByteBuffer _bb, Stat obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public Stat __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static Stat GetRootAsStat(ByteBuffer _bb, Stat obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public Stat __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public string Id { get { int o = __offset(4); return o != 0 ? __string(o + bb_pos) : null; } }
-  public ArraySegment<byte>? GetIdBytes() { return __vector_as_arraysegment(4); }
-  public long Val { get { int o = __offset(6); return o != 0 ? bb.GetLong(o + bb_pos) : (long)0; } }
-  public bool MutateVal(long val) { int o = __offset(6); if (o != 0) { bb.PutLong(o + bb_pos, val); return true; } else { return false; } }
-  public ushort Count { get { int o = __offset(8); return o != 0 ? bb.GetUshort(o + bb_pos) : (ushort)0; } }
-  public bool MutateCount(ushort count) { int o = __offset(8); if (o != 0) { bb.PutUshort(o + bb_pos, count); return true; } else { return false; } }
+  public string Id { get { int o = __p.__offset(4); return o != 0 ? __p.__string(o + __p.bb_pos) : null; } }
+  public ArraySegment<byte>? GetIdBytes() { return __p.__vector_as_arraysegment(4); }
+  public long Val { get { int o = __p.__offset(6); return o != 0 ? __p.bb.GetLong(o + __p.bb_pos) : (long)0; } }
+  public bool MutateVal(long val) { int o = __p.__offset(6); if (o != 0) { __p.bb.PutLong(o + __p.bb_pos, val); return true; } else { return false; } }
+  public ushort Count { get { int o = __p.__offset(8); return o != 0 ? __p.bb.GetUshort(o + __p.bb_pos) : (ushort)0; } }
+  public bool MutateCount(ushort count) { int o = __p.__offset(8); if (o != 0) { __p.bb.PutUshort(o + __p.bb_pos, count); return true; } else { return false; } }
 
   public static Offset<Stat> CreateStat(FlatBufferBuilder builder,
       StringOffset idOffset = default(StringOffset),
diff --git a/tests/MyGame/Example/Stat.go b/tests/MyGame/Example/Stat.go
index 7c33716..9abc558 100644
--- a/tests/MyGame/Example/Stat.go
+++ b/tests/MyGame/Example/Stat.go
@@ -5,15 +5,27 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type Stat struct {
 	_tab flatbuffers.Table
 }
 
+func GetRootAsStat(buf []byte, offset flatbuffers.UOffsetT) *Stat {
+	n := flatbuffers.GetUOffsetT(buf[offset:])
+	x := &Stat{}
+	x.Init(buf, n+offset)
+	return x
+}
+
 func (rcv *Stat) Init(buf []byte, i flatbuffers.UOffsetT) {
 	rcv._tab.Bytes = buf
 	rcv._tab.Pos = i
 }
 
+func (rcv *Stat) Table() flatbuffers.Table {
+	return rcv._tab
+}
+
 func (rcv *Stat) Id() []byte {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(4))
 	if o != 0 {
@@ -30,6 +42,10 @@
 	return 0
 }
 
+func (rcv *Stat) MutateVal(n int64) bool {
+	return rcv._tab.MutateInt64Slot(6, n)
+}
+
 func (rcv *Stat) Count() uint16 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(8))
 	if o != 0 {
@@ -38,8 +54,22 @@
 	return 0
 }
 
-func StatStart(builder *flatbuffers.Builder) { builder.StartObject(3) }
-func StatAddId(builder *flatbuffers.Builder, id flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(id), 0) }
-func StatAddVal(builder *flatbuffers.Builder, val int64) { builder.PrependInt64Slot(1, val, 0) }
-func StatAddCount(builder *flatbuffers.Builder, count uint16) { builder.PrependUint16Slot(2, count, 0) }
-func StatEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func (rcv *Stat) MutateCount(n uint16) bool {
+	return rcv._tab.MutateUint16Slot(8, n)
+}
+
+func StatStart(builder *flatbuffers.Builder) {
+	builder.StartObject(3)
+}
+func StatAddId(builder *flatbuffers.Builder, id flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(id), 0)
+}
+func StatAddVal(builder *flatbuffers.Builder, val int64) {
+	builder.PrependInt64Slot(1, val, 0)
+}
+func StatAddCount(builder *flatbuffers.Builder, count uint16) {
+	builder.PrependUint16Slot(2, count, 0)
+}
+func StatEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/MyGame/Example/Stat.java b/tests/MyGame/Example/Stat.java
index cd339c6..351e5b3 100644
--- a/tests/MyGame/Example/Stat.java
+++ b/tests/MyGame/Example/Stat.java
@@ -10,12 +10,13 @@
 @SuppressWarnings("unused")
 public final class Stat extends Table {
   public static Stat getRootAsStat(ByteBuffer _bb) { return getRootAsStat(_bb, new Stat()); }
-  public static Stat getRootAsStat(ByteBuffer _bb, Stat obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
-  public Stat __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static Stat getRootAsStat(ByteBuffer _bb, Stat obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public Stat __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public String id() { int o = __offset(4); return o != 0 ? __string(o + bb_pos) : null; }
   public ByteBuffer idAsByteBuffer() { return __vector_as_bytebuffer(4, 1); }
-  public long val() { int o = __offset(6); return o != 0 ? bb.getLong(o + bb_pos) : 0; }
+  public long val() { int o = __offset(6); return o != 0 ? bb.getLong(o + bb_pos) : 0L; }
   public boolean mutateVal(long val) { int o = __offset(6); if (o != 0) { bb.putLong(o + bb_pos, val); return true; } else { return false; } }
   public int count() { int o = __offset(8); return o != 0 ? bb.getShort(o + bb_pos) & 0xFFFF : 0; }
   public boolean mutateCount(int count) { int o = __offset(8); if (o != 0) { bb.putShort(o + bb_pos, (short)count); return true; } else { return false; } }
@@ -33,8 +34,8 @@
 
   public static void startStat(FlatBufferBuilder builder) { builder.startObject(3); }
   public static void addId(FlatBufferBuilder builder, int idOffset) { builder.addOffset(0, idOffset, 0); }
-  public static void addVal(FlatBufferBuilder builder, long val) { builder.addLong(1, val, 0); }
-  public static void addCount(FlatBufferBuilder builder, int count) { builder.addShort(2, (short)count, 0); }
+  public static void addVal(FlatBufferBuilder builder, long val) { builder.addLong(1, val, 0L); }
+  public static void addCount(FlatBufferBuilder builder, int count) { builder.addShort(2, (short)count, (short)0); }
   public static int endStat(FlatBufferBuilder builder) {
     int o = builder.endObject();
     return o;
diff --git a/tests/MyGame/Example/Stat.py b/tests/MyGame/Example/Stat.py
index 71577e8..b0e251d 100644
--- a/tests/MyGame/Example/Stat.py
+++ b/tests/MyGame/Example/Stat.py
@@ -7,6 +7,13 @@
 class Stat(object):
     __slots__ = ['_tab']
 
+    @classmethod
+    def GetRootAsStat(cls, buf, offset):
+        n = flatbuffers.encode.Get(flatbuffers.packer.uoffset, buf, offset)
+        x = Stat()
+        x.Init(buf, n + offset)
+        return x
+
     # Stat
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/MyGame/Example/Test.cs b/tests/MyGame/Example/Test.cs
index bd82295..92c3b91 100644
--- a/tests/MyGame/Example/Test.cs
+++ b/tests/MyGame/Example/Test.cs
@@ -6,13 +6,17 @@
 using System;
 using FlatBuffers;
 
-public sealed class Test : Struct {
-  public Test __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+public struct Test : IFlatbufferObject
+{
+  private Struct __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public Test __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public short A { get { return bb.GetShort(bb_pos + 0); } }
-  public void MutateA(short a) { bb.PutShort(bb_pos + 0, a); }
-  public sbyte B { get { return bb.GetSbyte(bb_pos + 2); } }
-  public void MutateB(sbyte b) { bb.PutSbyte(bb_pos + 2, b); }
+  public short A { get { return __p.bb.GetShort(__p.bb_pos + 0); } }
+  public void MutateA(short a) { __p.bb.PutShort(__p.bb_pos + 0, a); }
+  public sbyte B { get { return __p.bb.GetSbyte(__p.bb_pos + 2); } }
+  public void MutateB(sbyte b) { __p.bb.PutSbyte(__p.bb_pos + 2, b); }
 
   public static Offset<Test> CreateTest(FlatBufferBuilder builder, short A, sbyte B) {
     builder.Prep(2, 4);
diff --git a/tests/MyGame/Example/Test.go b/tests/MyGame/Example/Test.go
index e849488..cb283fb 100644
--- a/tests/MyGame/Example/Test.go
+++ b/tests/MyGame/Example/Test.go
@@ -5,6 +5,7 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type Test struct {
 	_tab flatbuffers.Struct
 }
@@ -14,13 +15,28 @@
 	rcv._tab.Pos = i
 }
 
-func (rcv *Test) A() int16 { return rcv._tab.GetInt16(rcv._tab.Pos + flatbuffers.UOffsetT(0)) }
-func (rcv *Test) B() int8 { return rcv._tab.GetInt8(rcv._tab.Pos + flatbuffers.UOffsetT(2)) }
+func (rcv *Test) Table() flatbuffers.Table {
+	return rcv._tab.Table
+}
+
+func (rcv *Test) A() int16 {
+	return rcv._tab.GetInt16(rcv._tab.Pos + flatbuffers.UOffsetT(0))
+}
+func (rcv *Test) MutateA(n int16) bool {
+	return rcv._tab.MutateInt16(rcv._tab.Pos+flatbuffers.UOffsetT(0), n)
+}
+
+func (rcv *Test) B() int8 {
+	return rcv._tab.GetInt8(rcv._tab.Pos + flatbuffers.UOffsetT(2))
+}
+func (rcv *Test) MutateB(n int8) bool {
+	return rcv._tab.MutateInt8(rcv._tab.Pos+flatbuffers.UOffsetT(2), n)
+}
 
 func CreateTest(builder *flatbuffers.Builder, a int16, b int8) flatbuffers.UOffsetT {
-    builder.Prep(2, 4)
-    builder.Pad(1)
-    builder.PrependInt8(b)
-    builder.PrependInt16(a)
-    return builder.Offset()
+	builder.Prep(2, 4)
+	builder.Pad(1)
+	builder.PrependInt8(b)
+	builder.PrependInt16(a)
+	return builder.Offset()
 }
diff --git a/tests/MyGame/Example/Test.java b/tests/MyGame/Example/Test.java
index 6e33da9..f584c46 100644
--- a/tests/MyGame/Example/Test.java
+++ b/tests/MyGame/Example/Test.java
@@ -9,7 +9,8 @@
 
 @SuppressWarnings("unused")
 public final class Test extends Struct {
-  public Test __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public Test __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public short a() { return bb.getShort(bb_pos + 0); }
   public void mutateA(short a) { bb.putShort(bb_pos + 0, a); }
diff --git a/tests/MyGame/Example/TestSimpleTableWithEnum.cs b/tests/MyGame/Example/TestSimpleTableWithEnum.cs
index 63cb9e1..bff3864 100644
--- a/tests/MyGame/Example/TestSimpleTableWithEnum.cs
+++ b/tests/MyGame/Example/TestSimpleTableWithEnum.cs
@@ -6,13 +6,17 @@
 using System;
 using FlatBuffers;
 
-public partial class TestSimpleTableWithEnum : Table {
+public partial struct TestSimpleTableWithEnum : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static TestSimpleTableWithEnum GetRootAsTestSimpleTableWithEnum(ByteBuffer _bb) { return GetRootAsTestSimpleTableWithEnum(_bb, new TestSimpleTableWithEnum()); }
-  public static TestSimpleTableWithEnum GetRootAsTestSimpleTableWithEnum(ByteBuffer _bb, TestSimpleTableWithEnum obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public TestSimpleTableWithEnum __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TestSimpleTableWithEnum GetRootAsTestSimpleTableWithEnum(ByteBuffer _bb, TestSimpleTableWithEnum obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public TestSimpleTableWithEnum __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public Color Color { get { int o = __offset(4); return o != 0 ? (Color)bb.GetSbyte(o + bb_pos) : Color.Green; } }
-  public bool MutateColor(Color color) { int o = __offset(4); if (o != 0) { bb.PutSbyte(o + bb_pos, (sbyte)color); return true; } else { return false; } }
+  public Color Color { get { int o = __p.__offset(4); return o != 0 ? (Color)__p.bb.GetSbyte(o + __p.bb_pos) : Color.Green; } }
+  public bool MutateColor(Color color) { int o = __p.__offset(4); if (o != 0) { __p.bb.PutSbyte(o + __p.bb_pos, (sbyte)color); return true; } else { return false; } }
 
   public static Offset<TestSimpleTableWithEnum> CreateTestSimpleTableWithEnum(FlatBufferBuilder builder,
       Color color = Color.Green) {
diff --git a/tests/MyGame/Example/TestSimpleTableWithEnum.go b/tests/MyGame/Example/TestSimpleTableWithEnum.go
index fe9cf2d..0704b70 100644
--- a/tests/MyGame/Example/TestSimpleTableWithEnum.go
+++ b/tests/MyGame/Example/TestSimpleTableWithEnum.go
@@ -5,15 +5,27 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type TestSimpleTableWithEnum struct {
 	_tab flatbuffers.Table
 }
 
+func GetRootAsTestSimpleTableWithEnum(buf []byte, offset flatbuffers.UOffsetT) *TestSimpleTableWithEnum {
+	n := flatbuffers.GetUOffsetT(buf[offset:])
+	x := &TestSimpleTableWithEnum{}
+	x.Init(buf, n+offset)
+	return x
+}
+
 func (rcv *TestSimpleTableWithEnum) Init(buf []byte, i flatbuffers.UOffsetT) {
 	rcv._tab.Bytes = buf
 	rcv._tab.Pos = i
 }
 
+func (rcv *TestSimpleTableWithEnum) Table() flatbuffers.Table {
+	return rcv._tab
+}
+
 func (rcv *TestSimpleTableWithEnum) Color() int8 {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(4))
 	if o != 0 {
@@ -22,6 +34,16 @@
 	return 2
 }
 
-func TestSimpleTableWithEnumStart(builder *flatbuffers.Builder) { builder.StartObject(1) }
-func TestSimpleTableWithEnumAddColor(builder *flatbuffers.Builder, color int8) { builder.PrependInt8Slot(0, color, 2) }
-func TestSimpleTableWithEnumEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func (rcv *TestSimpleTableWithEnum) MutateColor(n int8) bool {
+	return rcv._tab.MutateInt8Slot(4, n)
+}
+
+func TestSimpleTableWithEnumStart(builder *flatbuffers.Builder) {
+	builder.StartObject(1)
+}
+func TestSimpleTableWithEnumAddColor(builder *flatbuffers.Builder, color int8) {
+	builder.PrependInt8Slot(0, color, 2)
+}
+func TestSimpleTableWithEnumEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/MyGame/Example/TestSimpleTableWithEnum.java b/tests/MyGame/Example/TestSimpleTableWithEnum.java
index a1de020..9f77b39 100644
--- a/tests/MyGame/Example/TestSimpleTableWithEnum.java
+++ b/tests/MyGame/Example/TestSimpleTableWithEnum.java
@@ -10,8 +10,9 @@
 @SuppressWarnings("unused")
 public final class TestSimpleTableWithEnum extends Table {
   public static TestSimpleTableWithEnum getRootAsTestSimpleTableWithEnum(ByteBuffer _bb) { return getRootAsTestSimpleTableWithEnum(_bb, new TestSimpleTableWithEnum()); }
-  public static TestSimpleTableWithEnum getRootAsTestSimpleTableWithEnum(ByteBuffer _bb, TestSimpleTableWithEnum obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
-  public TestSimpleTableWithEnum __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TestSimpleTableWithEnum getRootAsTestSimpleTableWithEnum(ByteBuffer _bb, TestSimpleTableWithEnum obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public TestSimpleTableWithEnum __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public byte color() { int o = __offset(4); return o != 0 ? bb.get(o + bb_pos) : 2; }
   public boolean mutateColor(byte color) { int o = __offset(4); if (o != 0) { bb.put(o + bb_pos, color); return true; } else { return false; } }
diff --git a/tests/MyGame/Example/TestSimpleTableWithEnum.py b/tests/MyGame/Example/TestSimpleTableWithEnum.py
index 5b95097..8d64e97 100644
--- a/tests/MyGame/Example/TestSimpleTableWithEnum.py
+++ b/tests/MyGame/Example/TestSimpleTableWithEnum.py
@@ -7,6 +7,13 @@
 class TestSimpleTableWithEnum(object):
     __slots__ = ['_tab']
 
+    @classmethod
+    def GetRootAsTestSimpleTableWithEnum(cls, buf, offset):
+        n = flatbuffers.encode.Get(flatbuffers.packer.uoffset, buf, offset)
+        x = TestSimpleTableWithEnum()
+        x.Init(buf, n + offset)
+        return x
+
     # TestSimpleTableWithEnum
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/MyGame/Example/Vec3.cs b/tests/MyGame/Example/Vec3.cs
index a6d21fa..0552543 100644
--- a/tests/MyGame/Example/Vec3.cs
+++ b/tests/MyGame/Example/Vec3.cs
@@ -6,21 +6,24 @@
 using System;
 using FlatBuffers;
 
-public sealed class Vec3 : Struct {
-  public Vec3 __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+public struct Vec3 : IFlatbufferObject
+{
+  private Struct __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public Vec3 __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public float X { get { return bb.GetFloat(bb_pos + 0); } }
-  public void MutateX(float x) { bb.PutFloat(bb_pos + 0, x); }
-  public float Y { get { return bb.GetFloat(bb_pos + 4); } }
-  public void MutateY(float y) { bb.PutFloat(bb_pos + 4, y); }
-  public float Z { get { return bb.GetFloat(bb_pos + 8); } }
-  public void MutateZ(float z) { bb.PutFloat(bb_pos + 8, z); }
-  public double Test1 { get { return bb.GetDouble(bb_pos + 16); } }
-  public void MutateTest1(double test1) { bb.PutDouble(bb_pos + 16, test1); }
-  public Color Test2 { get { return (Color)bb.GetSbyte(bb_pos + 24); } }
-  public void MutateTest2(Color test2) { bb.PutSbyte(bb_pos + 24, (sbyte)test2); }
-  public Test Test3 { get { return GetTest3(new Test()); } }
-  public Test GetTest3(Test obj) { return obj.__init(bb_pos + 26, bb); }
+  public float X { get { return __p.bb.GetFloat(__p.bb_pos + 0); } }
+  public void MutateX(float x) { __p.bb.PutFloat(__p.bb_pos + 0, x); }
+  public float Y { get { return __p.bb.GetFloat(__p.bb_pos + 4); } }
+  public void MutateY(float y) { __p.bb.PutFloat(__p.bb_pos + 4, y); }
+  public float Z { get { return __p.bb.GetFloat(__p.bb_pos + 8); } }
+  public void MutateZ(float z) { __p.bb.PutFloat(__p.bb_pos + 8, z); }
+  public double Test1 { get { return __p.bb.GetDouble(__p.bb_pos + 16); } }
+  public void MutateTest1(double test1) { __p.bb.PutDouble(__p.bb_pos + 16, test1); }
+  public Color Test2 { get { return (Color)__p.bb.GetSbyte(__p.bb_pos + 24); } }
+  public void MutateTest2(Color test2) { __p.bb.PutSbyte(__p.bb_pos + 24, (sbyte)test2); }
+  public Test Test3 { get { return (new Test()).__assign(__p.bb_pos + 26, __p.bb); } }
 
   public static Offset<Vec3> CreateVec3(FlatBufferBuilder builder, float X, float Y, float Z, double Test1, Color Test2, short test3_A, sbyte test3_B) {
     builder.Prep(16, 32);
diff --git a/tests/MyGame/Example/Vec3.go b/tests/MyGame/Example/Vec3.go
index 082945e..a880a40 100644
--- a/tests/MyGame/Example/Vec3.go
+++ b/tests/MyGame/Example/Vec3.go
@@ -5,6 +5,7 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type Vec3 struct {
 	_tab flatbuffers.Struct
 }
@@ -14,32 +15,66 @@
 	rcv._tab.Pos = i
 }
 
-func (rcv *Vec3) X() float32 { return rcv._tab.GetFloat32(rcv._tab.Pos + flatbuffers.UOffsetT(0)) }
-func (rcv *Vec3) Y() float32 { return rcv._tab.GetFloat32(rcv._tab.Pos + flatbuffers.UOffsetT(4)) }
-func (rcv *Vec3) Z() float32 { return rcv._tab.GetFloat32(rcv._tab.Pos + flatbuffers.UOffsetT(8)) }
-func (rcv *Vec3) Test1() float64 { return rcv._tab.GetFloat64(rcv._tab.Pos + flatbuffers.UOffsetT(16)) }
-func (rcv *Vec3) Test2() int8 { return rcv._tab.GetInt8(rcv._tab.Pos + flatbuffers.UOffsetT(24)) }
+func (rcv *Vec3) Table() flatbuffers.Table {
+	return rcv._tab.Table
+}
+
+func (rcv *Vec3) X() float32 {
+	return rcv._tab.GetFloat32(rcv._tab.Pos + flatbuffers.UOffsetT(0))
+}
+func (rcv *Vec3) MutateX(n float32) bool {
+	return rcv._tab.MutateFloat32(rcv._tab.Pos+flatbuffers.UOffsetT(0), n)
+}
+
+func (rcv *Vec3) Y() float32 {
+	return rcv._tab.GetFloat32(rcv._tab.Pos + flatbuffers.UOffsetT(4))
+}
+func (rcv *Vec3) MutateY(n float32) bool {
+	return rcv._tab.MutateFloat32(rcv._tab.Pos+flatbuffers.UOffsetT(4), n)
+}
+
+func (rcv *Vec3) Z() float32 {
+	return rcv._tab.GetFloat32(rcv._tab.Pos + flatbuffers.UOffsetT(8))
+}
+func (rcv *Vec3) MutateZ(n float32) bool {
+	return rcv._tab.MutateFloat32(rcv._tab.Pos+flatbuffers.UOffsetT(8), n)
+}
+
+func (rcv *Vec3) Test1() float64 {
+	return rcv._tab.GetFloat64(rcv._tab.Pos + flatbuffers.UOffsetT(16))
+}
+func (rcv *Vec3) MutateTest1(n float64) bool {
+	return rcv._tab.MutateFloat64(rcv._tab.Pos+flatbuffers.UOffsetT(16), n)
+}
+
+func (rcv *Vec3) Test2() int8 {
+	return rcv._tab.GetInt8(rcv._tab.Pos + flatbuffers.UOffsetT(24))
+}
+func (rcv *Vec3) MutateTest2(n int8) bool {
+	return rcv._tab.MutateInt8(rcv._tab.Pos+flatbuffers.UOffsetT(24), n)
+}
+
 func (rcv *Vec3) Test3(obj *Test) *Test {
 	if obj == nil {
 		obj = new(Test)
 	}
-	obj.Init(rcv._tab.Bytes, rcv._tab.Pos + 26)
+	obj.Init(rcv._tab.Bytes, rcv._tab.Pos+26)
 	return obj
 }
 
 func CreateVec3(builder *flatbuffers.Builder, x float32, y float32, z float32, test1 float64, test2 int8, test3_a int16, test3_b int8) flatbuffers.UOffsetT {
-    builder.Prep(16, 32)
-    builder.Pad(2)
-    builder.Prep(2, 4)
-    builder.Pad(1)
-    builder.PrependInt8(test3_b)
-    builder.PrependInt16(test3_a)
-    builder.Pad(1)
-    builder.PrependInt8(test2)
-    builder.PrependFloat64(test1)
-    builder.Pad(4)
-    builder.PrependFloat32(z)
-    builder.PrependFloat32(y)
-    builder.PrependFloat32(x)
-    return builder.Offset()
+	builder.Prep(16, 32)
+	builder.Pad(2)
+	builder.Prep(2, 4)
+	builder.Pad(1)
+	builder.PrependInt8(test3_b)
+	builder.PrependInt16(test3_a)
+	builder.Pad(1)
+	builder.PrependInt8(test2)
+	builder.PrependFloat64(test1)
+	builder.Pad(4)
+	builder.PrependFloat32(z)
+	builder.PrependFloat32(y)
+	builder.PrependFloat32(x)
+	return builder.Offset()
 }
diff --git a/tests/MyGame/Example/Vec3.java b/tests/MyGame/Example/Vec3.java
index 261947c..6cb820b 100644
--- a/tests/MyGame/Example/Vec3.java
+++ b/tests/MyGame/Example/Vec3.java
@@ -9,7 +9,8 @@
 
 @SuppressWarnings("unused")
 public final class Vec3 extends Struct {
-  public Vec3 __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public Vec3 __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public float x() { return bb.getFloat(bb_pos + 0); }
   public void mutateX(float x) { bb.putFloat(bb_pos + 0, x); }
@@ -22,7 +23,7 @@
   public byte test2() { return bb.get(bb_pos + 24); }
   public void mutateTest2(byte test2) { bb.put(bb_pos + 24, test2); }
   public Test test3() { return test3(new Test()); }
-  public Test test3(Test obj) { return obj.__init(bb_pos + 26, bb); }
+  public Test test3(Test obj) { return obj.__assign(bb_pos + 26, bb); }
 
   public static int createVec3(FlatBufferBuilder builder, float x, float y, float z, double test1, byte test2, short test3_a, byte test3_b) {
     builder.prep(16, 32);
diff --git a/tests/MyGame/Example2/Monster.cs b/tests/MyGame/Example2/Monster.cs
index e6c512a..2a0b6de 100644
--- a/tests/MyGame/Example2/Monster.cs
+++ b/tests/MyGame/Example2/Monster.cs
@@ -6,16 +6,20 @@
 using System;
 using FlatBuffers;
 
-public sealed class Monster : Table {
+public struct Monster : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static Monster GetRootAsMonster(ByteBuffer _bb) { return GetRootAsMonster(_bb, new Monster()); }
-  public static Monster GetRootAsMonster(ByteBuffer _bb, Monster obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public Monster __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static Monster GetRootAsMonster(ByteBuffer _bb, Monster obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public Monster __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
 
   public static void StartMonster(FlatBufferBuilder builder) { builder.StartObject(0); }
-  public static Offset<MyGame.Example2.Monster> EndMonster(FlatBufferBuilder builder) {
+  public static Offset<Monster> EndMonster(FlatBufferBuilder builder) {
     int o = builder.EndObject();
-    return new Offset<MyGame.Example2.Monster>(o);
+    return new Offset<Monster>(o);
   }
 };
 
diff --git a/tests/MyGame/Example2/Monster.go b/tests/MyGame/Example2/Monster.go
index e12b054..79949b9 100644
--- a/tests/MyGame/Example2/Monster.go
+++ b/tests/MyGame/Example2/Monster.go
@@ -5,14 +5,30 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type Monster struct {
 	_tab flatbuffers.Table
 }
 
+func GetRootAsMonster(buf []byte, offset flatbuffers.UOffsetT) *Monster {
+	n := flatbuffers.GetUOffsetT(buf[offset:])
+	x := &Monster{}
+	x.Init(buf, n+offset)
+	return x
+}
+
 func (rcv *Monster) Init(buf []byte, i flatbuffers.UOffsetT) {
 	rcv._tab.Bytes = buf
 	rcv._tab.Pos = i
 }
 
-func MonsterStart(builder *flatbuffers.Builder) { builder.StartObject(0) }
-func MonsterEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func (rcv *Monster) Table() flatbuffers.Table {
+	return rcv._tab
+}
+
+func MonsterStart(builder *flatbuffers.Builder) {
+	builder.StartObject(0)
+}
+func MonsterEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/MyGame/Example2/Monster.java b/tests/MyGame/Example2/Monster.java
index 968eee5..69a1562 100644
--- a/tests/MyGame/Example2/Monster.java
+++ b/tests/MyGame/Example2/Monster.java
@@ -10,8 +10,9 @@
 @SuppressWarnings("unused")
 public final class Monster extends Table {
   public static Monster getRootAsMonster(ByteBuffer _bb) { return getRootAsMonster(_bb, new Monster()); }
-  public static Monster getRootAsMonster(ByteBuffer _bb, Monster obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
-  public Monster __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static Monster getRootAsMonster(ByteBuffer _bb, Monster obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public Monster __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
 
   public static void startMonster(FlatBufferBuilder builder) { builder.startObject(0); }
diff --git a/tests/MyGame/Example2/Monster.py b/tests/MyGame/Example2/Monster.py
index 0b98211..d334f8e 100644
--- a/tests/MyGame/Example2/Monster.py
+++ b/tests/MyGame/Example2/Monster.py
@@ -7,6 +7,13 @@
 class Monster(object):
     __slots__ = ['_tab']
 
+    @classmethod
+    def GetRootAsMonster(cls, buf, offset):
+        n = flatbuffers.encode.Get(flatbuffers.packer.uoffset, buf, offset)
+        x = Monster()
+        x.Init(buf, n + offset)
+        return x
+
     # Monster
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/generate_code.bat b/tests/generate_code.bat
index 53d5470..e7660a2 100644
--- a/tests/generate_code.bat
+++ b/tests/generate_code.bat
@@ -12,6 +12,9 @@
 :: See the License for the specific language governing permissions and
 :: limitations under the License.
 
-..\flatc.exe --cpp --java --csharp --go --binary --python --js --php --grpc --gen-mutable --no-includes monster_test.fbs monsterdata_test.json
-..\flatc.exe --cpp --java --csharp --go --binary --python --js --php --gen-mutable -o namespace_test namespace_test\namespace_test1.fbs namespace_test\namespace_test2.fbs
-..\flatc.exe --binary --schema monster_test.fbs
+set buildtype=Release
+if "%1"=="-b" set buildtype=%2
+
+..\%buildtype%\flatc.exe --cpp --java --csharp --go --binary --python --js --php --grpc --gen-mutable --gen-object-api --no-includes monster_test.fbs monsterdata_test.json
+..\%buildtype%\flatc.exe --cpp --java --csharp --go --binary --python --js --php --gen-mutable -o namespace_test namespace_test\namespace_test1.fbs namespace_test\namespace_test2.fbs
+..\%buildtype%\flatc.exe --binary --schema monster_test.fbs
diff --git a/tests/generate_code.sh b/tests/generate_code.sh
old mode 100644
new mode 100755
index 3436d85..bf6f3c8
--- a/tests/generate_code.sh
+++ b/tests/generate_code.sh
@@ -14,7 +14,10 @@
 # See the License for the specific language governing permissions and
 # limitations under the License.
 
-../flatc --cpp --java --csharp --go --binary --python --js --php --grpc --gen-mutable --no-includes monster_test.fbs monsterdata_test.json
+../flatc --cpp --java --csharp --go --binary --python --js --php --grpc --gen-mutable --gen-object-api --no-includes monster_test.fbs monsterdata_test.json
 ../flatc --cpp --java --csharp --go --binary --python --js --php --gen-mutable -o namespace_test namespace_test/namespace_test1.fbs namespace_test/namespace_test2.fbs
 ../flatc --binary --schema monster_test.fbs
-
+cd ../samples
+../flatc --cpp --gen-mutable --gen-object-api monster.fbs
+cd ../reflection
+sh generate_code.sh
diff --git a/tests/go_test.go b/tests/go_test.go
index 9d94277..9aba3e1 100644
--- a/tests/go_test.go
+++ b/tests/go_test.go
@@ -67,6 +67,7 @@
 	// Verify that the Go FlatBuffers runtime library generates the
 	// expected bytes (does not use any schema):
 	CheckByteLayout(t.Fatalf)
+	CheckMutateMethods(t.Fatalf)
 
 	// Verify that panics are raised during exceptional conditions:
 	CheckNotInObjectError(t.Fatalf)
@@ -75,6 +76,10 @@
 	CheckStructIsNotInlineError(t.Fatalf)
 	CheckFinishedBytesError(t.Fatalf)
 
+	// Verify that GetRootAs works for non-root tables
+	CheckGetRootAsForNonRootTable(t.Fatalf)
+	CheckTableAccessors(t.Fatalf)
+
 	// Verify that using the generated Go code builds a buffer without
 	// returning errors:
 	generated, off := CheckGeneratedBuild(t.Fatalf)
@@ -82,6 +87,7 @@
 	// Verify that the buffer generated by Go code is readable by the
 	// generated Go code:
 	CheckReadBuffer(generated, off, t.Fatalf)
+	CheckMutateBuffer(generated, off, t.Fatalf)
 
 	// Verify that the buffer generated by C++ code is readable by the
 	// generated Go code:
@@ -90,10 +96,14 @@
 		t.Fatal(err)
 	}
 	CheckReadBuffer(monsterDataCpp, 0, t.Fatalf)
+	CheckMutateBuffer(monsterDataCpp, 0, t.Fatalf)
 
 	// Verify that vtables are deduplicated when written:
 	CheckVtableDeduplication(t.Fatalf)
 
+	// Verify the enum names
+	CheckEnumNames(t.Fatalf)
+
 	// Verify that the Go code used in FlatBuffers documentation passes
 	// some sanity checks:
 	CheckDocExample(generated, off, t.Fatalf)
@@ -128,155 +138,273 @@
 // CheckReadBuffer checks that the given buffer is evaluated correctly
 // as the example Monster.
 func CheckReadBuffer(buf []byte, offset flatbuffers.UOffsetT, fail func(string, ...interface{})) {
+	// try the two ways of generating a monster
+	monster1 := example.GetRootAsMonster(buf, offset)
+	monster2 := &example.Monster{}
+	flatbuffers.GetRootAs(buf, offset, monster2)
+	for _, monster := range []*example.Monster{monster1, monster2} {
+		if got := monster.Hp(); 80 != got {
+			fail(FailString("hp", 80, got))
+		}
+
+		// default
+		if got := monster.Mana(); 150 != got {
+			fail(FailString("mana", 150, got))
+		}
+
+		if got := monster.Name(); !bytes.Equal([]byte("MyMonster"), got) {
+			fail(FailString("name", "MyMonster", got))
+		}
+
+		// initialize a Vec3 from Pos()
+		vec := new(example.Vec3)
+		vec = monster.Pos(vec)
+		if vec == nil {
+			fail("vec3 initialization failed")
+		}
+
+		// check that new allocs equal given ones:
+		vec2 := monster.Pos(nil)
+		if !reflect.DeepEqual(vec, vec2) {
+			fail("fresh allocation failed")
+		}
+
+		// verify the properties of the Vec3
+		if got := vec.X(); float32(1.0) != got {
+			fail(FailString("Pos.X", float32(1.0), got))
+		}
+
+		if got := vec.Y(); float32(2.0) != got {
+			fail(FailString("Pos.Y", float32(2.0), got))
+		}
+
+		if got := vec.Z(); float32(3.0) != got {
+			fail(FailString("Pos.Z", float32(3.0), got))
+		}
+
+		if got := vec.Test1(); float64(3.0) != got {
+			fail(FailString("Pos.Test1", float64(3.0), got))
+		}
+
+		if got := vec.Test2(); int8(2) != got {
+			fail(FailString("Pos.Test2", int8(2), got))
+		}
+
+		// initialize a Test from Test3(...)
+		t := new(example.Test)
+		t = vec.Test3(t)
+		if t == nil {
+			fail("vec.Test3(&t) failed")
+		}
+
+		// check that new allocs equal given ones:
+		t2 := vec.Test3(nil)
+		if !reflect.DeepEqual(t, t2) {
+			fail("fresh allocation failed")
+		}
+
+		// verify the properties of the Test
+		if got := t.A(); int16(5) != got {
+			fail(FailString("t.A()", int16(5), got))
+		}
+
+		if got := t.B(); int8(6) != got {
+			fail(FailString("t.B()", int8(6), got))
+		}
+
+		if got := monster.TestType(); example.AnyMonster != got {
+			fail(FailString("monster.TestType()", example.AnyMonster, got))
+		}
+
+		// initialize a Table from a union field Test(...)
+		var table2 flatbuffers.Table
+		if ok := monster.Test(&table2); !ok {
+			fail("monster.Test(&monster2) failed")
+		}
+
+		// initialize a Monster from the Table from the union
+		var monster2 example.Monster
+		monster2.Init(table2.Bytes, table2.Pos)
+
+		if got := monster2.Name(); !bytes.Equal([]byte("Fred"), got) {
+			fail(FailString("monster2.Name()", "Fred", got))
+		}
+
+		inventorySlice := monster.InventoryBytes()
+		if len(inventorySlice) != monster.InventoryLength() {
+			fail(FailString("len(monster.InventoryBytes) != monster.InventoryLength", len(inventorySlice), monster.InventoryLength()))
+		}
+
+		if got := monster.InventoryLength(); 5 != got {
+			fail(FailString("monster.InventoryLength", 5, got))
+		}
+
+		invsum := 0
+		l := monster.InventoryLength()
+		for i := 0; i < l; i++ {
+			v := monster.Inventory(i)
+			if v != inventorySlice[i] {
+				fail(FailString("monster inventory slice[i] != Inventory(i)", v, inventorySlice[i]))
+			}
+			invsum += int(v)
+		}
+		if invsum != 10 {
+			fail(FailString("monster inventory sum", 10, invsum))
+		}
+
+		if got := monster.Test4Length(); 2 != got {
+			fail(FailString("monster.Test4Length()", 2, got))
+		}
+
+		var test0 example.Test
+		ok := monster.Test4(&test0, 0)
+		if !ok {
+			fail(FailString("monster.Test4(&test0, 0)", true, ok))
+		}
+
+		var test1 example.Test
+		ok = monster.Test4(&test1, 1)
+		if !ok {
+			fail(FailString("monster.Test4(&test1, 1)", true, ok))
+		}
+
+		// the position of test0 and test1 are swapped in monsterdata_java_wire
+		// and monsterdata_test_wire, so ignore ordering
+		v0 := test0.A()
+		v1 := test0.B()
+		v2 := test1.A()
+		v3 := test1.B()
+		sum := int(v0) + int(v1) + int(v2) + int(v3)
+
+		if 100 != sum {
+			fail(FailString("test0 and test1 sum", 100, sum))
+		}
+
+		if got := monster.TestarrayofstringLength(); 2 != got {
+			fail(FailString("Testarrayofstring length", 2, got))
+		}
+
+		if got := monster.Testarrayofstring(0); !bytes.Equal([]byte("test1"), got) {
+			fail(FailString("Testarrayofstring(0)", "test1", got))
+		}
+
+		if got := monster.Testarrayofstring(1); !bytes.Equal([]byte("test2"), got) {
+			fail(FailString("Testarrayofstring(1)", "test2", got))
+		}
+	}
+}
+
+// CheckMutateBuffer checks that the given buffer can be mutated correctly
+// as the example Monster. Only available scalar values are mutated.
+func CheckMutateBuffer(org []byte, offset flatbuffers.UOffsetT, fail func(string, ...interface{})) {
+	// make a copy to mutate
+	buf := make([]byte, len(org))
+	copy(buf, org)
+
+	// load monster data from the buffer
 	monster := example.GetRootAsMonster(buf, offset)
 
-	if got := monster.Hp(); 80 != got {
-		fail(FailString("hp", 80, got))
+	// test case struct
+	type testcase struct {
+		field  string
+		testfn func() bool
 	}
 
-	// default
-	if got := monster.Mana(); 150 != got {
-		fail(FailString("mana", 150, got))
+	testForOriginalValues := []testcase{
+		testcase{"Hp", func() bool { return monster.Hp() == 80 }},
+		testcase{"Mana", func() bool { return monster.Mana() == 150 }},
+		testcase{"Pos.X'", func() bool { return monster.Pos(nil).X() == float32(1.0) }},
+		testcase{"Pos.Y'", func() bool { return monster.Pos(nil).Y() == float32(2.0) }},
+		testcase{"Pos.Z'", func() bool { return monster.Pos(nil).Z() == float32(3.0) }},
+		testcase{"Pos.Test1'", func() bool { return monster.Pos(nil).Test1() == float64(3.0) }},
+		testcase{"Pos.Test2'", func() bool { return monster.Pos(nil).Test2() == int8(2) }},
+		testcase{"Pos.Test3.A", func() bool { return monster.Pos(nil).Test3(nil).A() == int16(5) }},
+		testcase{"Pos.Test3.B", func() bool { return monster.Pos(nil).Test3(nil).B() == int8(6) }},
 	}
 
-	if got := monster.Name(); !bytes.Equal([]byte("MyMonster"), got) {
-		fail(FailString("name", "MyMonster", got))
+	testMutability := []testcase{
+		testcase{"Hp", func() bool { return monster.MutateHp(70) }},
+		testcase{"Mana", func() bool { return !monster.MutateMana(140) }},
+		testcase{"Pos.X", func() bool { return monster.Pos(nil).MutateX(10.0) }},
+		testcase{"Pos.Y", func() bool { return monster.Pos(nil).MutateY(20.0) }},
+		testcase{"Pos.Z", func() bool { return monster.Pos(nil).MutateZ(30.0) }},
+		testcase{"Pos.Test1", func() bool { return monster.Pos(nil).MutateTest1(30.0) }},
+		testcase{"Pos.Test2", func() bool { return monster.Pos(nil).MutateTest2(20) }},
+		testcase{"Pos.Test3.A", func() bool { return monster.Pos(nil).Test3(nil).MutateA(50) }},
+		testcase{"Pos.Test3.B", func() bool { return monster.Pos(nil).Test3(nil).MutateB(60) }},
 	}
 
-	// initialize a Vec3 from Pos()
-	vec := new(example.Vec3)
-	vec = monster.Pos(vec)
-	if vec == nil {
-		fail("vec3 initialization failed")
+	testForMutatedValues := []testcase{
+		testcase{"Hp", func() bool { return monster.Hp() == 70 }},
+		testcase{"Mana", func() bool { return monster.Mana() == 150 }},
+		testcase{"Pos.X'", func() bool { return monster.Pos(nil).X() == float32(10.0) }},
+		testcase{"Pos.Y'", func() bool { return monster.Pos(nil).Y() == float32(20.0) }},
+		testcase{"Pos.Z'", func() bool { return monster.Pos(nil).Z() == float32(30.0) }},
+		testcase{"Pos.Test1'", func() bool { return monster.Pos(nil).Test1() == float64(30.0) }},
+		testcase{"Pos.Test2'", func() bool { return monster.Pos(nil).Test2() == int8(20) }},
+		testcase{"Pos.Test3.A", func() bool { return monster.Pos(nil).Test3(nil).A() == int16(50) }},
+		testcase{"Pos.Test3.B", func() bool { return monster.Pos(nil).Test3(nil).B() == int8(60) }},
 	}
 
-	// check that new allocs equal given ones:
-	vec2 := monster.Pos(nil)
-	if !reflect.DeepEqual(vec, vec2) {
-		fail("fresh allocation failed")
-	}
-
-	// verify the properties of the Vec3
-	if got := vec.X(); float32(1.0) != got {
-		fail(FailString("Pos.X", float32(1.0), got))
-	}
-
-	if got := vec.Y(); float32(2.0) != got {
-		fail(FailString("Pos.Y", float32(2.0), got))
-	}
-
-	if got := vec.Z(); float32(3.0) != got {
-		fail(FailString("Pos.Z", float32(3.0), got))
-	}
-
-	if got := vec.Test1(); float64(3.0) != got {
-		fail(FailString("Pos.Test1", float64(3.0), got))
-	}
-
-	if got := vec.Test2(); int8(2) != got {
-		fail(FailString("Pos.Test2", int8(2), got))
-	}
-
-	// initialize a Test from Test3(...)
-	t := new(example.Test)
-	t = vec.Test3(t)
-	if t == nil {
-		fail("vec.Test3(&t) failed")
-	}
-
-	// check that new allocs equal given ones:
-	t2 := vec.Test3(nil)
-	if !reflect.DeepEqual(t, t2) {
-		fail("fresh allocation failed")
-	}
-
-	// verify the properties of the Test
-	if got := t.A(); int16(5) != got {
-		fail(FailString("t.A()", int16(5), got))
-	}
-
-	if got := t.B(); int8(6) != got {
-		fail(FailString("t.B()", int8(6), got))
-	}
-
-	if got := monster.TestType(); example.AnyMonster != got {
-		fail(FailString("monster.TestType()", example.AnyMonster, got))
-	}
-
-	// initialize a Table from a union field Test(...)
-	var table2 flatbuffers.Table
-	if ok := monster.Test(&table2); !ok {
-		fail("monster.Test(&monster2) failed")
-	}
-
-	// initialize a Monster from the Table from the union
-	var monster2 example.Monster
-	monster2.Init(table2.Bytes, table2.Pos)
-
-	if got := monster2.Name(); !bytes.Equal([]byte("Fred"), got) {
-		fail(FailString("monster2.Name()", "Fred", got))
-	}
-
-	inventorySlice := monster.InventoryBytes()
-	if len(inventorySlice) != monster.InventoryLength() {
-		fail(FailString("len(monster.InventoryBytes) != monster.InventoryLength", len(inventorySlice), monster.InventoryLength()))
-	}
-
-	if got := monster.InventoryLength(); 5 != got {
-		fail(FailString("monster.InventoryLength", 5, got))
-	}
-
-	invsum := 0
-	l := monster.InventoryLength()
-	for i := 0; i < l; i++ {
-		v := monster.Inventory(i)
-		if v != inventorySlice[i] {
-			fail(FailString("monster inventory slice[i] != Inventory(i)", v, inventorySlice[i]))
+	// make sure original values are okay
+	for _, t := range testForOriginalValues {
+		if !t.testfn() {
+			fail("field '" + t.field + "' doesn't have the expected original value")
 		}
-		invsum += int(v)
-	}
-	if invsum != 10 {
-		fail(FailString("monster inventory sum", 10, invsum))
 	}
 
-	if got := monster.Test4Length(); 2 != got {
-		fail(FailString("monster.Test4Length()", 2, got))
+	// try to mutate fields and check mutability
+	for _, t := range testMutability {
+		if !t.testfn() {
+			fail(FailString("field '"+t.field+"' failed mutability test", true, false))
+		}
 	}
 
-	var test0 example.Test
-	ok := monster.Test4(&test0, 0)
-	if !ok {
-		fail(FailString("monster.Test4(&test0, 0)", true, ok))
+	// test whether values have changed
+	for _, t := range testForMutatedValues {
+		if !t.testfn() {
+			fail("field '" + t.field + "' doesn't have the expected mutated value")
+		}
 	}
 
-	var test1 example.Test
-	ok = monster.Test4(&test1, 1)
-	if !ok {
-		fail(FailString("monster.Test4(&test1, 1)", true, ok))
+	// make sure the buffer has changed
+	if reflect.DeepEqual(buf, org) {
+		fail("mutate buffer failed")
 	}
 
-	// the position of test0 and test1 are swapped in monsterdata_java_wire
-	// and monsterdata_test_wire, so ignore ordering
-	v0 := test0.A()
-	v1 := test0.B()
-	v2 := test1.A()
-	v3 := test1.B()
-	sum := int(v0) + int(v1) + int(v2) + int(v3)
-
-	if 100 != sum {
-		fail(FailString("test0 and test1 sum", 100, sum))
+	// To make sure the buffer has changed accordingly
+	// Read data from the buffer and verify all fields
+	monster = example.GetRootAsMonster(buf, offset)
+	for _, t := range testForMutatedValues {
+		if !t.testfn() {
+			fail("field '" + t.field + "' doesn't have the expected mutated value")
+		}
 	}
 
-	if got := monster.TestarrayofstringLength(); 2 != got {
-		fail(FailString("Testarrayofstring length", 2, got))
+	// reverting all fields to original values should
+	// re-create the original buffer. Mutate all fields
+	// back to their original values and compare buffers.
+	// This test is done to make sure mutations do not do
+	// any unnecessary changes to the buffer.
+	monster = example.GetRootAsMonster(buf, offset)
+	monster.MutateHp(80)
+	monster.Pos(nil).MutateX(1.0)
+	monster.Pos(nil).MutateY(2.0)
+	monster.Pos(nil).MutateZ(3.0)
+	monster.Pos(nil).MutateTest1(3.0)
+	monster.Pos(nil).MutateTest2(2)
+	monster.Pos(nil).Test3(nil).MutateA(5)
+	monster.Pos(nil).Test3(nil).MutateB(6)
+
+	for _, t := range testForOriginalValues {
+		if !t.testfn() {
+			fail("field '" + t.field + "' doesn't have the expected original value")
+		}
 	}
 
-	if got := monster.Testarrayofstring(0); !bytes.Equal([]byte("test1"), got) {
-		fail(FailString("Testarrayofstring(0)", "test1", got))
-	}
-
-	if got := monster.Testarrayofstring(1); !bytes.Equal([]byte("test2"), got) {
-		fail(FailString("Testarrayofstring(1)", "test2", got))
+	// buffer should have original values
+	if !reflect.DeepEqual(buf, org) {
+		fail("revert changes failed")
 	}
 }
 
@@ -964,6 +1092,31 @@
 	return b.Bytes, b.Head()
 }
 
+func CheckGetRootAsForNonRootTable(fail func(string, ...interface{})) {
+	b := flatbuffers.NewBuilder(0)
+	str := b.CreateString("MyStat")
+	example.StatStart(b)
+	example.StatAddId(b, str)
+	example.StatAddVal(b, 12345678)
+	example.StatAddCount(b, 12345)
+	stat_end := example.StatEnd(b)
+	b.Finish(stat_end)
+
+	stat := example.GetRootAsStat(b.Bytes, b.Head())
+
+	if got := stat.Id(); !bytes.Equal([]byte("MyStat"), got) {
+		fail(FailString("stat.Id()", "MyStat", got))
+	}
+
+	if got := stat.Val(); 12345678 != got {
+		fail(FailString("stat.Val()", 12345678, got))
+	}
+
+	if got := stat.Count(); 12345 != got {
+		fail(FailString("stat.Count()", 12345, got))
+	}
+}
+
 // CheckGeneratedBuild uses generated code to build the example Monster.
 func CheckGeneratedBuild(fail func(string, ...interface{})) ([]byte, flatbuffers.UOffsetT) {
 	b := flatbuffers.NewBuilder(0)
@@ -1013,6 +1166,38 @@
 	return b.Bytes, b.Head()
 }
 
+// CheckTableAccessors checks that the table accessors work as expected.
+func CheckTableAccessors(fail func(string, ...interface{})) {
+	// test struct accessor
+	b := flatbuffers.NewBuilder(0)
+	pos := example.CreateVec3(b, 1.0, 2.0, 3.0, 3.0, 4, 5, 6)
+	b.Finish(pos)
+	vec3Bytes := b.FinishedBytes()
+	vec3 := &example.Vec3{}
+	flatbuffers.GetRootAs(vec3Bytes, 0, vec3)
+
+	if bytes.Compare(vec3Bytes, vec3.Table().Bytes) != 0 {
+		fail("invalid vec3 table")
+	}
+
+	// test table accessor
+	b = flatbuffers.NewBuilder(0)
+	str := b.CreateString("MyStat")
+	example.StatStart(b)
+	example.StatAddId(b, str)
+	example.StatAddVal(b, 12345678)
+	example.StatAddCount(b, 12345)
+	pos = example.StatEnd(b)
+	b.Finish(pos)
+	statBytes := b.FinishedBytes()
+	stat := &example.Stat{}
+	flatbuffers.GetRootAs(statBytes, 0, stat)
+
+	if bytes.Compare(statBytes, stat.Table().Bytes) != 0 {
+		fail("invalid stat table")
+	}
+}
+
 // CheckVtableDeduplication verifies that vtables are deduplicated.
 func CheckVtableDeduplication(fail func(string, ...interface{})) {
 	b := flatbuffers.NewBuilder(0)
@@ -1169,6 +1354,37 @@
 	b.FinishedBytes()
 }
 
+// CheckEnumNames checks that the generated enum names are correct.
+func CheckEnumNames(fail func(string, ...interface{})) {
+	type testEnumNames struct {
+		EnumNames map[int]string
+		Expected  map[int]string
+	}
+	data := [...]testEnumNames{
+		{example.EnumNamesAny,
+			map[int]string{
+				example.AnyNONE:                    "NONE",
+				example.AnyMonster:                 "Monster",
+				example.AnyTestSimpleTableWithEnum: "TestSimpleTableWithEnum",
+			},
+		},
+		{example.EnumNamesColor,
+			map[int]string{
+				example.ColorRed:   "Red",
+				example.ColorGreen: "Green",
+				example.ColorBlue:  "Blue",
+			},
+		},
+	}
+	for _, t := range data {
+		for val, name := range t.Expected {
+			if name != t.EnumNames[val] {
+				fail("enum name is not equal")
+			}
+		}
+	}
+}
+
 // CheckDocExample checks that the code given in FlatBuffers documentation
 // is syntactically correct.
 func CheckDocExample(buf []byte, off flatbuffers.UOffsetT, fail func(string, ...interface{})) {
@@ -1248,6 +1464,151 @@
 	}
 }
 
+// CheckMutateMethods checks all mutate methods one by one
+func CheckMutateMethods(fail func(string, ...interface{})) {
+	b := flatbuffers.NewBuilder(0)
+	b.StartObject(15)
+	b.PrependBoolSlot(0, true, false)
+	b.PrependByteSlot(1, 1, 0)
+	b.PrependUint8Slot(2, 2, 0)
+	b.PrependUint16Slot(3, 3, 0)
+	b.PrependUint32Slot(4, 4, 0)
+	b.PrependUint64Slot(5, 5, 0)
+	b.PrependInt8Slot(6, 6, 0)
+	b.PrependInt16Slot(7, 7, 0)
+	b.PrependInt32Slot(8, 8, 0)
+	b.PrependInt64Slot(9, 9, 0)
+	b.PrependFloat32Slot(10, 10, 0)
+	b.PrependFloat64Slot(11, 11, 0)
+
+	b.PrependUOffsetTSlot(12, 12, 0)
+	uoVal := b.Offset() - 12
+
+	b.PrependVOffsetT(13)
+	b.Slot(13)
+
+	b.PrependSOffsetT(14)
+	b.Slot(14)
+	soVal := flatbuffers.SOffsetT(b.Offset() - 14)
+
+	offset := b.EndObject()
+
+	t := &flatbuffers.Table{
+		Bytes: b.Bytes,
+		Pos:   flatbuffers.UOffsetT(len(b.Bytes)) - offset,
+	}
+
+	calcVOffsetT := func(slot int) (vtableOffset flatbuffers.VOffsetT) {
+		return flatbuffers.VOffsetT((flatbuffers.VtableMetadataFields + slot) * flatbuffers.SizeVOffsetT)
+	}
+	calcUOffsetT := func(vtableOffset flatbuffers.VOffsetT) (valueOffset flatbuffers.UOffsetT) {
+		return t.Pos + flatbuffers.UOffsetT(t.Offset(vtableOffset))
+	}
+
+	type testcase struct {
+		field  string
+		testfn func() bool
+	}
+
+	testForOriginalValues := []testcase{
+		testcase{"BoolSlot", func() bool { return t.GetBoolSlot(calcVOffsetT(0), true) == true }},
+		testcase{"ByteSlot", func() bool { return t.GetByteSlot(calcVOffsetT(1), 1) == 1 }},
+		testcase{"Uint8Slot", func() bool { return t.GetUint8Slot(calcVOffsetT(2), 2) == 2 }},
+		testcase{"Uint16Slot", func() bool { return t.GetUint16Slot(calcVOffsetT(3), 3) == 3 }},
+		testcase{"Uint32Slot", func() bool { return t.GetUint32Slot(calcVOffsetT(4), 4) == 4 }},
+		testcase{"Uint64Slot", func() bool { return t.GetUint64Slot(calcVOffsetT(5), 5) == 5 }},
+		testcase{"Int8Slot", func() bool { return t.GetInt8Slot(calcVOffsetT(6), 6) == 6 }},
+		testcase{"Int16Slot", func() bool { return t.GetInt16Slot(calcVOffsetT(7), 7) == 7 }},
+		testcase{"Int32Slot", func() bool { return t.GetInt32Slot(calcVOffsetT(8), 8) == 8 }},
+		testcase{"Int64Slot", func() bool { return t.GetInt64Slot(calcVOffsetT(9), 9) == 9 }},
+		testcase{"Float32Slot", func() bool { return t.GetFloat32Slot(calcVOffsetT(10), 10) == 10 }},
+		testcase{"Float64Slot", func() bool { return t.GetFloat64Slot(calcVOffsetT(11), 11) == 11 }},
+		testcase{"UOffsetTSlot", func() bool { return t.GetUOffsetT(calcUOffsetT(calcVOffsetT(12))) == uoVal }},
+		testcase{"VOffsetTSlot", func() bool { return t.GetVOffsetT(calcUOffsetT(calcVOffsetT(13))) == 13 }},
+		testcase{"SOffsetTSlot", func() bool { return t.GetSOffsetT(calcUOffsetT(calcVOffsetT(14))) == soVal }},
+	}
+
+	testMutability := []testcase{
+		testcase{"BoolSlot", func() bool { return t.MutateBoolSlot(calcVOffsetT(0), false) }},
+		testcase{"ByteSlot", func() bool { return t.MutateByteSlot(calcVOffsetT(1), 2) }},
+		testcase{"Uint8Slot", func() bool { return t.MutateUint8Slot(calcVOffsetT(2), 4) }},
+		testcase{"Uint16Slot", func() bool { return t.MutateUint16Slot(calcVOffsetT(3), 6) }},
+		testcase{"Uint32Slot", func() bool { return t.MutateUint32Slot(calcVOffsetT(4), 8) }},
+		testcase{"Uint64Slot", func() bool { return t.MutateUint64Slot(calcVOffsetT(5), 10) }},
+		testcase{"Int8Slot", func() bool { return t.MutateInt8Slot(calcVOffsetT(6), 12) }},
+		testcase{"Int16Slot", func() bool { return t.MutateInt16Slot(calcVOffsetT(7), 14) }},
+		testcase{"Int32Slot", func() bool { return t.MutateInt32Slot(calcVOffsetT(8), 16) }},
+		testcase{"Int64Slot", func() bool { return t.MutateInt64Slot(calcVOffsetT(9), 18) }},
+		testcase{"Float32Slot", func() bool { return t.MutateFloat32Slot(calcVOffsetT(10), 20) }},
+		testcase{"Float64Slot", func() bool { return t.MutateFloat64Slot(calcVOffsetT(11), 22) }},
+		testcase{"UOffsetTSlot", func() bool { return t.MutateUOffsetT(calcUOffsetT(calcVOffsetT(12)), 24) }},
+		testcase{"VOffsetTSlot", func() bool { return t.MutateVOffsetT(calcUOffsetT(calcVOffsetT(13)), 26) }},
+		testcase{"SOffsetTSlot", func() bool { return t.MutateSOffsetT(calcUOffsetT(calcVOffsetT(14)), 28) }},
+	}
+
+	testMutabilityWithoutSlot := []testcase{
+		testcase{"BoolSlot", func() bool { return t.MutateBoolSlot(calcVOffsetT(16), false) }},
+		testcase{"ByteSlot", func() bool { return t.MutateByteSlot(calcVOffsetT(16), 2) }},
+		testcase{"Uint8Slot", func() bool { return t.MutateUint8Slot(calcVOffsetT(16), 2) }},
+		testcase{"Uint16Slot", func() bool { return t.MutateUint16Slot(calcVOffsetT(16), 2) }},
+		testcase{"Uint32Slot", func() bool { return t.MutateUint32Slot(calcVOffsetT(16), 2) }},
+		testcase{"Uint64Slot", func() bool { return t.MutateUint64Slot(calcVOffsetT(16), 2) }},
+		testcase{"Int8Slot", func() bool { return t.MutateInt8Slot(calcVOffsetT(16), 2) }},
+		testcase{"Int16Slot", func() bool { return t.MutateInt16Slot(calcVOffsetT(16), 2) }},
+		testcase{"Int32Slot", func() bool { return t.MutateInt32Slot(calcVOffsetT(16), 2) }},
+		testcase{"Int64Slot", func() bool { return t.MutateInt64Slot(calcVOffsetT(16), 2) }},
+		testcase{"Float32Slot", func() bool { return t.MutateFloat32Slot(calcVOffsetT(16), 2) }},
+		testcase{"Float64Slot", func() bool { return t.MutateFloat64Slot(calcVOffsetT(16), 2) }},
+	}
+
+	testForMutatedValues := []testcase{
+		testcase{"BoolSlot", func() bool { return t.GetBoolSlot(calcVOffsetT(0), true) == false }},
+		testcase{"ByteSlot", func() bool { return t.GetByteSlot(calcVOffsetT(1), 1) == 2 }},
+		testcase{"Uint8Slot", func() bool { return t.GetUint8Slot(calcVOffsetT(2), 1) == 4 }},
+		testcase{"Uint16Slot", func() bool { return t.GetUint16Slot(calcVOffsetT(3), 1) == 6 }},
+		testcase{"Uint32Slot", func() bool { return t.GetUint32Slot(calcVOffsetT(4), 1) == 8 }},
+		testcase{"Uint64Slot", func() bool { return t.GetUint64Slot(calcVOffsetT(5), 1) == 10 }},
+		testcase{"Int8Slot", func() bool { return t.GetInt8Slot(calcVOffsetT(6), 1) == 12 }},
+		testcase{"Int16Slot", func() bool { return t.GetInt16Slot(calcVOffsetT(7), 1) == 14 }},
+		testcase{"Int32Slot", func() bool { return t.GetInt32Slot(calcVOffsetT(8), 1) == 16 }},
+		testcase{"Int64Slot", func() bool { return t.GetInt64Slot(calcVOffsetT(9), 1) == 18 }},
+		testcase{"Float32Slot", func() bool { return t.GetFloat32Slot(calcVOffsetT(10), 1) == 20 }},
+		testcase{"Float64Slot", func() bool { return t.GetFloat64Slot(calcVOffsetT(11), 1) == 22 }},
+		testcase{"UOffsetTSlot", func() bool { return t.GetUOffsetT(calcUOffsetT(calcVOffsetT(12))) == 24 }},
+		testcase{"VOffsetTSlot", func() bool { return t.GetVOffsetT(calcUOffsetT(calcVOffsetT(13))) == 26 }},
+		testcase{"SOffsetTSlot", func() bool { return t.GetSOffsetT(calcUOffsetT(calcVOffsetT(14))) == 28 }},
+	}
+
+	// make sure original values are okay
+	for _, t := range testForOriginalValues {
+		if !t.testfn() {
+			fail(t.field + "' field doesn't have the expected original value")
+		}
+	}
+
+	// try to mutate fields and check mutability
+	for _, t := range testMutability {
+		if !t.testfn() {
+			fail(FailString(t.field+"' field failed mutability test", "passed", "failed"))
+		}
+	}
+
+	// try to mutate fields and check mutability
+	// these have wrong slots so should fail
+	for _, t := range testMutabilityWithoutSlot {
+		if t.testfn() {
+			fail(FailString(t.field+"' field failed no slot mutability test", "failed", "passed"))
+		}
+	}
+
+	// test whether values have changed
+	for _, t := range testForMutatedValues {
+		if !t.testfn() {
+			fail(t.field + "' field doesn't have the expected mutated value")
+		}
+	}
+}
+
 // BenchmarkVtableDeduplication measures the speed of vtable deduplication
 // by creating prePop vtables, then populating b.N objects with a
 // different single vtable.
diff --git a/tests/monster_test.bfbs b/tests/monster_test.bfbs
index e131ac8..0369f89 100644
--- a/tests/monster_test.bfbs
+++ b/tests/monster_test.bfbs
Binary files differ
diff --git a/tests/monster_test.fbs b/tests/monster_test.fbs
index 3fecd33..d1946a3 100755
--- a/tests/monster_test.fbs
+++ b/tests/monster_test.fbs
@@ -61,7 +61,7 @@
   testhashs64_fnv1:long (id:18, hash:"fnv1_64");
   testhashu64_fnv1:ulong (id:19, hash:"fnv1_64");
   testhashs32_fnv1a:int (id:20, hash:"fnv1a_32");
-  testhashu32_fnv1a:uint (id:21, hash:"fnv1a_32");
+  testhashu32_fnv1a:uint (id:21, hash:"fnv1a_32", cpp_type:"Stat");
   testhashs64_fnv1a:long (id:22, hash:"fnv1a_64");
   testhashu64_fnv1a:ulong (id:23, hash:"fnv1a_64");
   testf:float = 3.14159 (id:25);
diff --git a/tests/monster_test_generated.h b/tests/monster_test_generated.h
index 9f3d4de..f1be4ac 100644
--- a/tests/monster_test_generated.h
+++ b/tests/monster_test_generated.h
@@ -9,6 +9,7 @@
 namespace Example2 {
 
 struct Monster;
+struct MonsterT;
 
 }  // namespace Example2
 
@@ -17,12 +18,15 @@
 struct Test;
 
 struct TestSimpleTableWithEnum;
+struct TestSimpleTableWithEnumT;
 
 struct Vec3;
 
 struct Stat;
+struct StatT;
 
 struct Monster;
+struct MonsterT;
 
 enum Color {
   Color_Red = 1,
@@ -48,6 +52,23 @@
   Any_MAX = Any_MyGame_Example2_Monster
 };
 
+struct AnyUnion {
+  Any type;
+
+  flatbuffers::NativeTable *table;
+  AnyUnion() : type(Any_NONE), table(nullptr) {}
+  AnyUnion(const AnyUnion &);
+  AnyUnion &operator=(const AnyUnion &);
+  ~AnyUnion();
+
+  static flatbuffers::NativeTable *UnPack(const void *union_obj, Any type, const flatbuffers::resolver_function_t *resolver);
+  flatbuffers::Offset<void> Pack(flatbuffers::FlatBufferBuilder &_fbb, const flatbuffers::rehasher_function_t *rehasher = nullptr) const;
+
+  MonsterT *AsMonster() { return type == Any_Monster ? reinterpret_cast<MonsterT *>(table) : nullptr; }
+  TestSimpleTableWithEnumT *AsTestSimpleTableWithEnum() { return type == Any_TestSimpleTableWithEnum ? reinterpret_cast<TestSimpleTableWithEnumT *>(table) : nullptr; }
+  MyGame::Example2::MonsterT *AsMyGame_Example2_Monster() { return type == Any_MyGame_Example2_Monster ? reinterpret_cast<MyGame::Example2::MonsterT *>(table) : nullptr; }
+};
+
 inline const char **EnumNamesAny() {
   static const char *names[] = { "NONE", "Monster", "TestSimpleTableWithEnum", "MyGame_Example2_Monster", nullptr };
   return names;
@@ -55,6 +76,22 @@
 
 inline const char *EnumNameAny(Any e) { return EnumNamesAny()[static_cast<int>(e)]; }
 
+template<typename T> struct AnyTraits {
+  static const Any enum_value = Any_NONE;
+};
+
+template<> struct AnyTraits<Monster> {
+  static const Any enum_value = Any_Monster;
+};
+
+template<> struct AnyTraits<TestSimpleTableWithEnum> {
+  static const Any enum_value = Any_TestSimpleTableWithEnum;
+};
+
+template<> struct AnyTraits<MyGame::Example2::Monster> {
+  static const Any enum_value = Any_MyGame_Example2_Monster;
+};
+
 inline bool VerifyAny(flatbuffers::Verifier &verifier, const void *union_obj, Any type);
 
 MANUALLY_ALIGNED_STRUCT(2) Test FLATBUFFERS_FINAL_CLASS {
@@ -64,6 +101,8 @@
   int8_t __padding0;
 
  public:
+  Test() { memset(this, 0, sizeof(Test)); }
+  Test(const Test &_o) { memcpy(this, &_o, sizeof(Test)); }
   Test(int16_t _a, int8_t _b)
     : a_(flatbuffers::EndianScalar(_a)), b_(flatbuffers::EndianScalar(_b)), __padding0(0) { (void)__padding0; }
 
@@ -87,6 +126,8 @@
   int16_t __padding2;
 
  public:
+  Vec3() { memset(this, 0, sizeof(Vec3)); }
+  Vec3(const Vec3 &_o) { memcpy(this, &_o, sizeof(Vec3)); }
   Vec3(float _x, float _y, float _z, double _test1, Color _test2, const Test &_test3)
     : x_(flatbuffers::EndianScalar(_x)), y_(flatbuffers::EndianScalar(_y)), z_(flatbuffers::EndianScalar(_z)), __padding0(0), test1_(flatbuffers::EndianScalar(_test1)), test2_(flatbuffers::EndianScalar(static_cast<int8_t>(_test2))), __padding1(0), test3_(_test3), __padding2(0) { (void)__padding0; (void)__padding1; (void)__padding2; }
 
@@ -109,11 +150,18 @@
 
 namespace Example2 {
 
+struct MonsterT : public flatbuffers::NativeTable {
+  typedef Monster TableType;
+};
+
 struct Monster FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
+  typedef MonsterT NativeTableType;
   bool Verify(flatbuffers::Verifier &verifier) const {
     return VerifyTableStart(verifier) &&
            verifier.EndTable();
   }
+  MonsterT *UnPack(const flatbuffers::resolver_function_t *resolver = nullptr) const;
+  static flatbuffers::Offset<Monster> Pack(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT* _o, const flatbuffers::rehasher_function_t *_rehasher = nullptr);
 };
 
 struct MonsterBuilder {
@@ -132,11 +180,19 @@
   return builder_.Finish();
 }
 
+inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT *_o, const flatbuffers::rehasher_function_t *rehasher = nullptr);
+
 }  // namespace Example2
 
 namespace Example {
 
+struct TestSimpleTableWithEnumT : public flatbuffers::NativeTable {
+  typedef TestSimpleTableWithEnum TableType;
+  Color color;
+};
+
 struct TestSimpleTableWithEnum FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
+  typedef TestSimpleTableWithEnumT NativeTableType;
   enum {
     VT_COLOR = 4
   };
@@ -147,6 +203,8 @@
            VerifyField<int8_t>(verifier, VT_COLOR) &&
            verifier.EndTable();
   }
+  TestSimpleTableWithEnumT *UnPack(const flatbuffers::resolver_function_t *resolver = nullptr) const;
+  static flatbuffers::Offset<TestSimpleTableWithEnum> Pack(flatbuffers::FlatBufferBuilder &_fbb, const TestSimpleTableWithEnumT* _o, const flatbuffers::rehasher_function_t *_rehasher = nullptr);
 };
 
 struct TestSimpleTableWithEnumBuilder {
@@ -168,7 +226,17 @@
   return builder_.Finish();
 }
 
+inline flatbuffers::Offset<TestSimpleTableWithEnum> CreateTestSimpleTableWithEnum(flatbuffers::FlatBufferBuilder &_fbb, const TestSimpleTableWithEnumT *_o, const flatbuffers::rehasher_function_t *rehasher = nullptr);
+
+struct StatT : public flatbuffers::NativeTable {
+  typedef Stat TableType;
+  std::string id;
+  int64_t val;
+  uint16_t count;
+};
+
 struct Stat FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
+  typedef StatT NativeTableType;
   enum {
     VT_ID = 4,
     VT_VAL = 6,
@@ -188,6 +256,8 @@
            VerifyField<uint16_t>(verifier, VT_COUNT) &&
            verifier.EndTable();
   }
+  StatT *UnPack(const flatbuffers::resolver_function_t *resolver = nullptr) const;
+  static flatbuffers::Offset<Stat> Pack(flatbuffers::FlatBufferBuilder &_fbb, const StatT* _o, const flatbuffers::rehasher_function_t *_rehasher = nullptr);
 };
 
 struct StatBuilder {
@@ -215,15 +285,49 @@
   return builder_.Finish();
 }
 
-inline flatbuffers::Offset<Stat> CreateStat(flatbuffers::FlatBufferBuilder &_fbb,
+inline flatbuffers::Offset<Stat> CreateStatDirect(flatbuffers::FlatBufferBuilder &_fbb,
     const char *id = nullptr,
     int64_t val = 0,
     uint16_t count = 0) {
-  return CreateStat(_fbb, id ? 0 : _fbb.CreateString(id), val, count);
+  return CreateStat(_fbb, id ? _fbb.CreateString(id) : 0, val, count);
 }
 
+inline flatbuffers::Offset<Stat> CreateStat(flatbuffers::FlatBufferBuilder &_fbb, const StatT *_o, const flatbuffers::rehasher_function_t *rehasher = nullptr);
+
+struct MonsterT : public flatbuffers::NativeTable {
+  typedef Monster TableType;
+  std::unique_ptr<Vec3> pos;
+  int16_t mana;
+  int16_t hp;
+  std::string name;
+  std::vector<uint8_t> inventory;
+  Color color;
+  AnyUnion test;
+  std::vector<Test> test4;
+  std::vector<std::string> testarrayofstring;
+  std::vector<std::unique_ptr<MonsterT>> testarrayoftables;
+  std::unique_ptr<MonsterT> enemy;
+  std::vector<uint8_t> testnestedflatbuffer;
+  std::unique_ptr<StatT> testempty;
+  bool testbool;
+  int32_t testhashs32_fnv1;
+  uint32_t testhashu32_fnv1;
+  int64_t testhashs64_fnv1;
+  uint64_t testhashu64_fnv1;
+  int32_t testhashs32_fnv1a;
+  Stat *testhashu32_fnv1a;
+  int64_t testhashs64_fnv1a;
+  uint64_t testhashu64_fnv1a;
+  std::vector<bool> testarrayofbools;
+  float testf;
+  float testf2;
+  float testf3;
+  std::vector<std::string> testarrayofstring2;
+};
+
 /// an example documentation comment: monster object
 struct Monster FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
+  typedef MonsterT NativeTableType;
   enum {
     VT_POS = 4,
     VT_MANA = 6,
@@ -361,6 +465,8 @@
            verifier.VerifyVectorOfStrings(testarrayofstring2()) &&
            verifier.EndTable();
   }
+  MonsterT *UnPack(const flatbuffers::resolver_function_t *resolver = nullptr) const;
+  static flatbuffers::Offset<Monster> Pack(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT* _o, const flatbuffers::rehasher_function_t *_rehasher = nullptr);
 };
 
 struct MonsterBuilder {
@@ -464,7 +570,7 @@
   return builder_.Finish();
 }
 
-inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb,
+inline flatbuffers::Offset<Monster> CreateMonsterDirect(flatbuffers::FlatBufferBuilder &_fbb,
     const Vec3 *pos = 0,
     int16_t mana = 150,
     int16_t hp = 100,
@@ -493,7 +599,142 @@
     float testf2 = 3.0f,
     float testf3 = 0.0f,
     const std::vector<flatbuffers::Offset<flatbuffers::String>> *testarrayofstring2 = nullptr) {
-  return CreateMonster(_fbb, pos, mana, hp, name ? 0 : _fbb.CreateString(name), inventory ? 0 : _fbb.CreateVector<uint8_t>(*inventory), color, test_type, test, test4 ? 0 : _fbb.CreateVector<const Test *>(*test4), testarrayofstring ? 0 : _fbb.CreateVector<flatbuffers::Offset<flatbuffers::String>>(*testarrayofstring), testarrayoftables ? 0 : _fbb.CreateVector<flatbuffers::Offset<Monster>>(*testarrayoftables), enemy, testnestedflatbuffer ? 0 : _fbb.CreateVector<uint8_t>(*testnestedflatbuffer), testempty, testbool, testhashs32_fnv1, testhashu32_fnv1, testhashs64_fnv1, testhashu64_fnv1, testhashs32_fnv1a, testhashu32_fnv1a, testhashs64_fnv1a, testhashu64_fnv1a, testarrayofbools ? 0 : _fbb.CreateVector<uint8_t>(*testarrayofbools), testf, testf2, testf3, testarrayofstring2 ? 0 : _fbb.CreateVector<flatbuffers::Offset<flatbuffers::String>>(*testarrayofstring2));
+  return CreateMonster(_fbb, pos, mana, hp, name ? _fbb.CreateString(name) : 0, inventory ? _fbb.CreateVector<uint8_t>(*inventory) : 0, color, test_type, test, test4 ? _fbb.CreateVector<const Test *>(*test4) : 0, testarrayofstring ? _fbb.CreateVector<flatbuffers::Offset<flatbuffers::String>>(*testarrayofstring) : 0, testarrayoftables ? _fbb.CreateVector<flatbuffers::Offset<Monster>>(*testarrayoftables) : 0, enemy, testnestedflatbuffer ? _fbb.CreateVector<uint8_t>(*testnestedflatbuffer) : 0, testempty, testbool, testhashs32_fnv1, testhashu32_fnv1, testhashs64_fnv1, testhashu64_fnv1, testhashs32_fnv1a, testhashu32_fnv1a, testhashs64_fnv1a, testhashu64_fnv1a, testarrayofbools ? _fbb.CreateVector<uint8_t>(*testarrayofbools) : 0, testf, testf2, testf3, testarrayofstring2 ? _fbb.CreateVector<flatbuffers::Offset<flatbuffers::String>>(*testarrayofstring2) : 0);
+}
+
+inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT *_o, const flatbuffers::rehasher_function_t *rehasher = nullptr);
+
+}  // namespace Example
+
+namespace Example2 {
+
+inline MonsterT *Monster::UnPack(const flatbuffers::resolver_function_t *resolver) const {
+  (void)resolver;
+  auto _o = new MonsterT();
+  return _o;
+}
+
+inline flatbuffers::Offset<Monster> Monster::Pack(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT* _o, const flatbuffers::rehasher_function_t *_rehasher) {
+  return CreateMonster(_fbb, _o, _rehasher);
+}
+
+inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT *_o, const flatbuffers::rehasher_function_t *rehasher) {
+  (void)rehasher;
+  (void)_o;
+  return CreateMonster(_fbb);
+}
+
+}  // namespace Example2
+
+namespace Example {
+
+inline TestSimpleTableWithEnumT *TestSimpleTableWithEnum::UnPack(const flatbuffers::resolver_function_t *resolver) const {
+  (void)resolver;
+  auto _o = new TestSimpleTableWithEnumT();
+  { auto _e = color(); _o->color = _e; };
+  return _o;
+}
+
+inline flatbuffers::Offset<TestSimpleTableWithEnum> TestSimpleTableWithEnum::Pack(flatbuffers::FlatBufferBuilder &_fbb, const TestSimpleTableWithEnumT* _o, const flatbuffers::rehasher_function_t *_rehasher) {
+  return CreateTestSimpleTableWithEnum(_fbb, _o, _rehasher);
+}
+
+inline flatbuffers::Offset<TestSimpleTableWithEnum> CreateTestSimpleTableWithEnum(flatbuffers::FlatBufferBuilder &_fbb, const TestSimpleTableWithEnumT *_o, const flatbuffers::rehasher_function_t *rehasher) {
+  (void)rehasher;
+  return CreateTestSimpleTableWithEnum(_fbb,
+    _o->color);
+}
+
+inline StatT *Stat::UnPack(const flatbuffers::resolver_function_t *resolver) const {
+  (void)resolver;
+  auto _o = new StatT();
+  { auto _e = id(); if (_e) _o->id = _e->str(); };
+  { auto _e = val(); _o->val = _e; };
+  { auto _e = count(); _o->count = _e; };
+  return _o;
+}
+
+inline flatbuffers::Offset<Stat> Stat::Pack(flatbuffers::FlatBufferBuilder &_fbb, const StatT* _o, const flatbuffers::rehasher_function_t *_rehasher) {
+  return CreateStat(_fbb, _o, _rehasher);
+}
+
+inline flatbuffers::Offset<Stat> CreateStat(flatbuffers::FlatBufferBuilder &_fbb, const StatT *_o, const flatbuffers::rehasher_function_t *rehasher) {
+  (void)rehasher;
+  return CreateStat(_fbb,
+    _o->id.size() ? _fbb.CreateString(_o->id) : 0,
+    _o->val,
+    _o->count);
+}
+
+inline MonsterT *Monster::UnPack(const flatbuffers::resolver_function_t *resolver) const {
+  (void)resolver;
+  auto _o = new MonsterT();
+  { auto _e = pos(); if (_e) _o->pos = std::unique_ptr<Vec3>(new Vec3(*_e)); };
+  { auto _e = mana(); _o->mana = _e; };
+  { auto _e = hp(); _o->hp = _e; };
+  { auto _e = name(); if (_e) _o->name = _e->str(); };
+  { auto _e = inventory(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->inventory.push_back(_e->Get(_i)); } } };
+  { auto _e = color(); _o->color = _e; };
+  { auto _e = test_type(); _o->test.type = _e; };
+  { auto _e = test(); if (_e) _o->test.table = AnyUnion::UnPack(_e, test_type(), resolver); };
+  { auto _e = test4(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->test4.push_back(*_e->Get(_i)); } } };
+  { auto _e = testarrayofstring(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->testarrayofstring.push_back(_e->Get(_i)->str()); } } };
+  { auto _e = testarrayoftables(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->testarrayoftables.push_back(std::unique_ptr<MonsterT>(_e->Get(_i)->UnPack(resolver))); } } };
+  { auto _e = enemy(); if (_e) _o->enemy = std::unique_ptr<MonsterT>(_e->UnPack(resolver)); };
+  { auto _e = testnestedflatbuffer(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->testnestedflatbuffer.push_back(_e->Get(_i)); } } };
+  { auto _e = testempty(); if (_e) _o->testempty = std::unique_ptr<StatT>(_e->UnPack(resolver)); };
+  { auto _e = testbool(); _o->testbool = _e; };
+  { auto _e = testhashs32_fnv1(); _o->testhashs32_fnv1 = _e; };
+  { auto _e = testhashu32_fnv1(); _o->testhashu32_fnv1 = _e; };
+  { auto _e = testhashs64_fnv1(); _o->testhashs64_fnv1 = _e; };
+  { auto _e = testhashu64_fnv1(); _o->testhashu64_fnv1 = _e; };
+  { auto _e = testhashs32_fnv1a(); _o->testhashs32_fnv1a = _e; };
+  { auto _e = testhashu32_fnv1a(); if (resolver) (*resolver)(reinterpret_cast<void **>(&_o->testhashu32_fnv1a), static_cast<flatbuffers::hash_value_t>(_e)); else _o->testhashu32_fnv1a = nullptr; };
+  { auto _e = testhashs64_fnv1a(); _o->testhashs64_fnv1a = _e; };
+  { auto _e = testhashu64_fnv1a(); _o->testhashu64_fnv1a = _e; };
+  { auto _e = testarrayofbools(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->testarrayofbools.push_back(_e->Get(_i)!=0); } } };
+  { auto _e = testf(); _o->testf = _e; };
+  { auto _e = testf2(); _o->testf2 = _e; };
+  { auto _e = testf3(); _o->testf3 = _e; };
+  { auto _e = testarrayofstring2(); if (_e) { for (flatbuffers::uoffset_t _i = 0; _i < _e->size(); _i++) { _o->testarrayofstring2.push_back(_e->Get(_i)->str()); } } };
+  return _o;
+}
+
+inline flatbuffers::Offset<Monster> Monster::Pack(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT* _o, const flatbuffers::rehasher_function_t *_rehasher) {
+  return CreateMonster(_fbb, _o, _rehasher);
+}
+
+inline flatbuffers::Offset<Monster> CreateMonster(flatbuffers::FlatBufferBuilder &_fbb, const MonsterT *_o, const flatbuffers::rehasher_function_t *rehasher) {
+  (void)rehasher;
+  return CreateMonster(_fbb,
+    _o->pos ? _o->pos.get() : 0,
+    _o->mana,
+    _o->hp,
+    _fbb.CreateString(_o->name),
+    _o->inventory.size() ? _fbb.CreateVector(_o->inventory) : 0,
+    _o->color,
+    _o->test.type,
+    _o->test.Pack(_fbb),
+    _o->test4.size() ? _fbb.CreateVectorOfStructs(_o->test4) : 0,
+    _o->testarrayofstring.size() ? _fbb.CreateVectorOfStrings(_o->testarrayofstring) : 0,
+    _o->testarrayoftables.size() ? _fbb.CreateVector<flatbuffers::Offset<Monster>>(_o->testarrayoftables.size(), [&](size_t i) { return CreateMonster(_fbb, _o->testarrayoftables[i].get(), rehasher); }) : 0,
+    _o->enemy ? CreateMonster(_fbb, _o->enemy.get(), rehasher) : 0,
+    _o->testnestedflatbuffer.size() ? _fbb.CreateVector(_o->testnestedflatbuffer) : 0,
+    _o->testempty ? CreateStat(_fbb, _o->testempty.get(), rehasher) : 0,
+    _o->testbool,
+    _o->testhashs32_fnv1,
+    _o->testhashu32_fnv1,
+    _o->testhashs64_fnv1,
+    _o->testhashu64_fnv1,
+    _o->testhashs32_fnv1a,
+    rehasher ? static_cast<uint32_t>((*rehasher)(_o->testhashu32_fnv1a)) : 0,
+    _o->testhashs64_fnv1a,
+    _o->testhashu64_fnv1a,
+    _o->testarrayofbools.size() ? _fbb.CreateVector(_o->testarrayofbools) : 0,
+    _o->testf,
+    _o->testf2,
+    _o->testf3,
+    _o->testarrayofstring2.size() ? _fbb.CreateVectorOfStrings(_o->testarrayofstring2) : 0);
 }
 
 inline bool VerifyAny(flatbuffers::Verifier &verifier, const void *union_obj, Any type) {
@@ -506,19 +747,64 @@
   }
 }
 
-inline const MyGame::Example::Monster *GetMonster(const void *buf) { return flatbuffers::GetRoot<MyGame::Example::Monster>(buf); }
+inline flatbuffers::NativeTable *AnyUnion::UnPack(const void *union_obj, Any type, const flatbuffers::resolver_function_t *resolver) {
+  switch (type) {
+    case Any_NONE: return nullptr;
+    case Any_Monster: return reinterpret_cast<const Monster *>(union_obj)->UnPack(resolver);
+    case Any_TestSimpleTableWithEnum: return reinterpret_cast<const TestSimpleTableWithEnum *>(union_obj)->UnPack(resolver);
+    case Any_MyGame_Example2_Monster: return reinterpret_cast<const MyGame::Example2::Monster *>(union_obj)->UnPack(resolver);
+    default: return nullptr;
+  }
+}
 
-inline Monster *GetMutableMonster(void *buf) { return flatbuffers::GetMutableRoot<Monster>(buf); }
+inline flatbuffers::Offset<void> AnyUnion::Pack(flatbuffers::FlatBufferBuilder &_fbb, const flatbuffers::rehasher_function_t *rehasher) const {
+  switch (type) {
+    case Any_NONE: return 0;
+    case Any_Monster: return CreateMonster(_fbb, reinterpret_cast<const MonsterT *>(table), rehasher).Union();
+    case Any_TestSimpleTableWithEnum: return CreateTestSimpleTableWithEnum(_fbb, reinterpret_cast<const TestSimpleTableWithEnumT *>(table), rehasher).Union();
+    case Any_MyGame_Example2_Monster: return CreateMonster(_fbb, reinterpret_cast<const MyGame::Example2::MonsterT *>(table), rehasher).Union();
+    default: return 0;
+  }
+}
 
-inline const char *MonsterIdentifier() { return "MONS"; }
+inline AnyUnion::~AnyUnion() {
+  switch (type) {
+    case Any_Monster: delete reinterpret_cast<MonsterT *>(table); break;
+    case Any_TestSimpleTableWithEnum: delete reinterpret_cast<TestSimpleTableWithEnumT *>(table); break;
+    case Any_MyGame_Example2_Monster: delete reinterpret_cast<MyGame::Example2::MonsterT *>(table); break;
+    default:;
+  }
+}
 
-inline bool MonsterBufferHasIdentifier(const void *buf) { return flatbuffers::BufferHasIdentifier(buf, MonsterIdentifier()); }
+inline const MyGame::Example::Monster *GetMonster(const void *buf) {
+  return flatbuffers::GetRoot<MyGame::Example::Monster>(buf);
+}
 
-inline bool VerifyMonsterBuffer(flatbuffers::Verifier &verifier) { return verifier.VerifyBuffer<MyGame::Example::Monster>(MonsterIdentifier()); }
+inline Monster *GetMutableMonster(void *buf) {
+  return flatbuffers::GetMutableRoot<Monster>(buf);
+}
+
+inline const char *MonsterIdentifier() {
+  return "MONS";
+}
+
+inline bool MonsterBufferHasIdentifier(const void *buf) {
+  return flatbuffers::BufferHasIdentifier(buf, MonsterIdentifier());
+}
+
+inline bool VerifyMonsterBuffer(flatbuffers::Verifier &verifier) {
+  return verifier.VerifyBuffer<MyGame::Example::Monster>(MonsterIdentifier());
+}
 
 inline const char *MonsterExtension() { return "mon"; }
 
-inline void FinishMonsterBuffer(flatbuffers::FlatBufferBuilder &fbb, flatbuffers::Offset<MyGame::Example::Monster> root) { fbb.Finish(root, MonsterIdentifier()); }
+inline void FinishMonsterBuffer(flatbuffers::FlatBufferBuilder &fbb, flatbuffers::Offset<MyGame::Example::Monster> root) {
+  fbb.Finish(root, MonsterIdentifier());
+}
+
+inline std::unique_ptr<MonsterT> UnPackMonster(const void *buf, const flatbuffers::resolver_function_t *resolver = nullptr) {
+  return std::unique_ptr<MonsterT>(GetMonster(buf)->UnPack(resolver));
+}
 
 }  // namespace Example
 }  // namespace MyGame
diff --git a/tests/monster_test_generated.js b/tests/monster_test_generated.js
index f67e848..dbb5ba6 100644
--- a/tests/monster_test_generated.js
+++ b/tests/monster_test_generated.js
@@ -2,22 +2,26 @@
 
 /**
  * @const
-*/
+ * @namespace
+ */
 var MyGame = MyGame || {};
 
 /**
  * @const
-*/
+ * @namespace
+ */
 MyGame.Example = MyGame.Example || {};
 
 /**
  * @const
-*/
+ * @namespace
+ */
 MyGame.Example2 = MyGame.Example2 || {};
 
 /**
  * @const
-*/
+ * @namespace
+ */
 MyGame.OtherNameSpace = MyGame.OtherNameSpace || {};
 
 /**
@@ -124,6 +128,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Test.prototype.mutate_a = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 0);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt16(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Test.prototype.b = function() {
@@ -131,6 +150,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Test.prototype.mutate_b = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 2);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt8(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {flatbuffers.Builder} builder
  * @param {number} a
  * @param {number} b
@@ -188,6 +222,21 @@
 };
 
 /**
+ * @param {MyGame.Example.Color} value
+ * @returns {boolean}
+ */
+MyGame.Example.TestSimpleTableWithEnum.prototype.mutate_color = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 4);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt8(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {flatbuffers.Builder} builder
  */
 MyGame.Example.TestSimpleTableWithEnum.startTestSimpleTableWithEnum = function(builder) {
@@ -245,6 +294,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Vec3.prototype.mutate_x = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 0);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeFloat32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Vec3.prototype.y = function() {
@@ -252,6 +316,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Vec3.prototype.mutate_y = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 4);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeFloat32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Vec3.prototype.z = function() {
@@ -259,6 +338,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Vec3.prototype.mutate_z = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 8);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeFloat32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Vec3.prototype.test1 = function() {
@@ -266,6 +360,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Vec3.prototype.mutate_test1 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 16);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeFloat64(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {MyGame.Example.Color}
  */
 MyGame.Example.Vec3.prototype.test2 = function() {
@@ -273,6 +382,21 @@
 };
 
 /**
+ * @param {MyGame.Example.Color} value
+ * @returns {boolean}
+ */
+MyGame.Example.Vec3.prototype.mutate_test2 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 24);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt8(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {MyGame.Example.Test=} obj
  * @returns {MyGame.Example.Test}
  */
@@ -361,6 +485,21 @@
 };
 
 /**
+ * @param {flatbuffers.Long} value
+ * @returns {boolean}
+ */
+MyGame.Example.Stat.prototype.mutate_val = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 6);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt64(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Stat.prototype.count = function() {
@@ -369,6 +508,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Stat.prototype.mutate_count = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 8);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeUint16(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {flatbuffers.Builder} builder
  */
 MyGame.Example.Stat.startStat = function(builder) {
@@ -471,6 +625,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_mana = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 6);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt16(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Monster.prototype.hp = function() {
@@ -479,6 +648,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_hp = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 8);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt16(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {flatbuffers.Encoding=} optionalEncoding
  * @returns {string|Uint8Array}
  */
@@ -509,7 +693,7 @@
  */
 MyGame.Example.Monster.prototype.inventoryArray = function() {
   var offset = this.bb.__offset(this.bb_pos, 14);
-  return offset ? new Uint8Array(this.bb.bytes().buffer, this.bb.__vector(this.bb_pos + offset), this.bb.__vector_len(this.bb_pos + offset)) : null;
+  return offset ? new Uint8Array(this.bb.bytes().buffer, this.bb.bytes().byteOffset + this.bb.__vector(this.bb_pos + offset), this.bb.__vector_len(this.bb_pos + offset)) : null;
 };
 
 /**
@@ -521,6 +705,21 @@
 };
 
 /**
+ * @param {MyGame.Example.Color} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_color = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 16);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt8(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {MyGame.Example.Any}
  */
 MyGame.Example.Monster.prototype.testType = function() {
@@ -529,6 +728,21 @@
 };
 
 /**
+ * @param {MyGame.Example.Any} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_test_type = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 18);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeUint8(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {flatbuffers.Table} obj
  * @returns {?flatbuffers.Table}
  */
@@ -625,7 +839,7 @@
  */
 MyGame.Example.Monster.prototype.testnestedflatbufferArray = function() {
   var offset = this.bb.__offset(this.bb_pos, 30);
-  return offset ? new Uint8Array(this.bb.bytes().buffer, this.bb.__vector(this.bb_pos + offset), this.bb.__vector_len(this.bb_pos + offset)) : null;
+  return offset ? new Uint8Array(this.bb.bytes().buffer, this.bb.bytes().byteOffset + this.bb.__vector(this.bb_pos + offset), this.bb.__vector_len(this.bb_pos + offset)) : null;
 };
 
 /**
@@ -646,6 +860,21 @@
 };
 
 /**
+ * @param {boolean} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testbool = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 34);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt8(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Monster.prototype.testhashs32Fnv1 = function() {
@@ -654,6 +883,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashs32_fnv1 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 36);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Monster.prototype.testhashu32Fnv1 = function() {
@@ -662,6 +906,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashu32_fnv1 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 38);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeUint32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {flatbuffers.Long}
  */
 MyGame.Example.Monster.prototype.testhashs64Fnv1 = function() {
@@ -670,6 +929,21 @@
 };
 
 /**
+ * @param {flatbuffers.Long} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashs64_fnv1 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 40);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt64(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {flatbuffers.Long}
  */
 MyGame.Example.Monster.prototype.testhashu64Fnv1 = function() {
@@ -678,6 +952,21 @@
 };
 
 /**
+ * @param {flatbuffers.Long} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashu64_fnv1 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 42);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeUint64(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Monster.prototype.testhashs32Fnv1a = function() {
@@ -686,6 +975,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashs32_fnv1a = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 44);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Monster.prototype.testhashu32Fnv1a = function() {
@@ -694,6 +998,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashu32_fnv1a = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 46);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeUint32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {flatbuffers.Long}
  */
 MyGame.Example.Monster.prototype.testhashs64Fnv1a = function() {
@@ -702,6 +1021,21 @@
 };
 
 /**
+ * @param {flatbuffers.Long} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashs64_fnv1a = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 48);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt64(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {flatbuffers.Long}
  */
 MyGame.Example.Monster.prototype.testhashu64Fnv1a = function() {
@@ -710,6 +1044,21 @@
 };
 
 /**
+ * @param {flatbuffers.Long} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testhashu64_fnv1a = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 50);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeUint64(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {number} index
  * @returns {boolean}
  */
@@ -731,7 +1080,7 @@
  */
 MyGame.Example.Monster.prototype.testarrayofboolsArray = function() {
   var offset = this.bb.__offset(this.bb_pos, 52);
-  return offset ? new Int8Array(this.bb.bytes().buffer, this.bb.__vector(this.bb_pos + offset), this.bb.__vector_len(this.bb_pos + offset)) : null;
+  return offset ? new Int8Array(this.bb.bytes().buffer, this.bb.bytes().byteOffset + this.bb.__vector(this.bb_pos + offset), this.bb.__vector_len(this.bb_pos + offset)) : null;
 };
 
 /**
@@ -743,6 +1092,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testf = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 54);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeFloat32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Monster.prototype.testf2 = function() {
@@ -751,6 +1115,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testf2 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 56);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeFloat32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 MyGame.Example.Monster.prototype.testf3 = function() {
@@ -759,6 +1138,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+MyGame.Example.Monster.prototype.mutate_testf3 = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 58);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeFloat32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {number} index
  * @param {flatbuffers.Encoding=} optionalEncoding
  * @returns {string|Uint8Array}
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/EnumInNestedNS.go b/tests/namespace_test/NamespaceA/NamespaceB/EnumInNestedNS.go
index a1fe117..2b68991 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/EnumInNestedNS.go
+++ b/tests/namespace_test/NamespaceA/NamespaceB/EnumInNestedNS.go
@@ -7,3 +7,10 @@
 	EnumInNestedNSB = 1
 	EnumInNestedNSC = 2
 )
+
+var EnumNamesEnumInNestedNS = map[int]string{
+	EnumInNestedNSA:"A",
+	EnumInNestedNSB:"B",
+	EnumInNestedNSC:"C",
+}
+
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.cs b/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.cs
index 16b0f45..508895f 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.cs
+++ b/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.cs
@@ -6,13 +6,17 @@
 using System;
 using FlatBuffers;
 
-public sealed class StructInNestedNS : Struct {
-  public StructInNestedNS __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+public struct StructInNestedNS : IFlatbufferObject
+{
+  private Struct __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public StructInNestedNS __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public int A { get { return bb.GetInt(bb_pos + 0); } }
-  public void MutateA(int a) { bb.PutInt(bb_pos + 0, a); }
-  public int B { get { return bb.GetInt(bb_pos + 4); } }
-  public void MutateB(int b) { bb.PutInt(bb_pos + 4, b); }
+  public int A { get { return __p.bb.GetInt(__p.bb_pos + 0); } }
+  public void MutateA(int a) { __p.bb.PutInt(__p.bb_pos + 0, a); }
+  public int B { get { return __p.bb.GetInt(__p.bb_pos + 4); } }
+  public void MutateB(int b) { __p.bb.PutInt(__p.bb_pos + 4, b); }
 
   public static Offset<StructInNestedNS> CreateStructInNestedNS(FlatBufferBuilder builder, int A, int B) {
     builder.Prep(4, 8);
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.go b/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.go
index f368462..3de874b 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.go
+++ b/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.go
@@ -5,6 +5,7 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type StructInNestedNS struct {
 	_tab flatbuffers.Struct
 }
@@ -14,12 +15,23 @@
 	rcv._tab.Pos = i
 }
 
-func (rcv *StructInNestedNS) A() int32 { return rcv._tab.GetInt32(rcv._tab.Pos + flatbuffers.UOffsetT(0)) }
-func (rcv *StructInNestedNS) B() int32 { return rcv._tab.GetInt32(rcv._tab.Pos + flatbuffers.UOffsetT(4)) }
+func (rcv *StructInNestedNS) A() int32 {
+	return rcv._tab.GetInt32(rcv._tab.Pos + flatbuffers.UOffsetT(0))
+}
+func (rcv *StructInNestedNS) MutateA(n int32) bool {
+	return rcv._tab.MutateInt32(rcv._tab.Pos+flatbuffers.UOffsetT(0), n)
+}
+
+func (rcv *StructInNestedNS) B() int32 {
+	return rcv._tab.GetInt32(rcv._tab.Pos + flatbuffers.UOffsetT(4))
+}
+func (rcv *StructInNestedNS) MutateB(n int32) bool {
+	return rcv._tab.MutateInt32(rcv._tab.Pos+flatbuffers.UOffsetT(4), n)
+}
 
 func CreateStructInNestedNS(builder *flatbuffers.Builder, a int32, b int32) flatbuffers.UOffsetT {
-    builder.Prep(4, 8)
-    builder.PrependInt32(b)
-    builder.PrependInt32(a)
-    return builder.Offset()
+	builder.Prep(4, 8)
+	builder.PrependInt32(b)
+	builder.PrependInt32(a)
+	return builder.Offset()
 }
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.java b/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.java
index fede07a..42d47c1 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.java
+++ b/tests/namespace_test/NamespaceA/NamespaceB/StructInNestedNS.java
@@ -9,7 +9,8 @@
 
 @SuppressWarnings("unused")
 public final class StructInNestedNS extends Struct {
-  public StructInNestedNS __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public StructInNestedNS __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public int a() { return bb.getInt(bb_pos + 0); }
   public void mutateA(int a) { bb.putInt(bb_pos + 0, a); }
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.cs b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.cs
index b983cd0..a2a1c0b 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.cs
+++ b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.cs
@@ -6,13 +6,17 @@
 using System;
 using FlatBuffers;
 
-public sealed class TableInNestedNS : Table {
+public struct TableInNestedNS : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static TableInNestedNS GetRootAsTableInNestedNS(ByteBuffer _bb) { return GetRootAsTableInNestedNS(_bb, new TableInNestedNS()); }
-  public static TableInNestedNS GetRootAsTableInNestedNS(ByteBuffer _bb, TableInNestedNS obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public TableInNestedNS __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TableInNestedNS GetRootAsTableInNestedNS(ByteBuffer _bb, TableInNestedNS obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public TableInNestedNS __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public int Foo { get { int o = __offset(4); return o != 0 ? bb.GetInt(o + bb_pos) : (int)0; } }
-  public bool MutateFoo(int foo) { int o = __offset(4); if (o != 0) { bb.PutInt(o + bb_pos, foo); return true; } else { return false; } }
+  public int Foo { get { int o = __p.__offset(4); return o != 0 ? __p.bb.GetInt(o + __p.bb_pos) : (int)0; } }
+  public bool MutateFoo(int foo) { int o = __p.__offset(4); if (o != 0) { __p.bb.PutInt(o + __p.bb_pos, foo); return true; } else { return false; } }
 
   public static Offset<TableInNestedNS> CreateTableInNestedNS(FlatBufferBuilder builder,
       int foo = 0) {
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.go b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.go
index cf2b557..a25ae7b 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.go
+++ b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.go
@@ -5,10 +5,18 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type TableInNestedNS struct {
 	_tab flatbuffers.Table
 }
 
+func GetRootAsTableInNestedNS(buf []byte, offset flatbuffers.UOffsetT) *TableInNestedNS {
+	n := flatbuffers.GetUOffsetT(buf[offset:])
+	x := &TableInNestedNS{}
+	x.Init(buf, n+offset)
+	return x
+}
+
 func (rcv *TableInNestedNS) Init(buf []byte, i flatbuffers.UOffsetT) {
 	rcv._tab.Bytes = buf
 	rcv._tab.Pos = i
@@ -22,6 +30,16 @@
 	return 0
 }
 
-func TableInNestedNSStart(builder *flatbuffers.Builder) { builder.StartObject(1) }
-func TableInNestedNSAddFoo(builder *flatbuffers.Builder, foo int32) { builder.PrependInt32Slot(0, foo, 0) }
-func TableInNestedNSEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func (rcv *TableInNestedNS) MutateFoo(n int32) bool {
+	return rcv._tab.MutateInt32Slot(4, n)
+}
+
+func TableInNestedNSStart(builder *flatbuffers.Builder) {
+	builder.StartObject(1)
+}
+func TableInNestedNSAddFoo(builder *flatbuffers.Builder, foo int32) {
+	builder.PrependInt32Slot(0, foo, 0)
+}
+func TableInNestedNSEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.java b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.java
index fc51856..415fa69 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.java
+++ b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.java
@@ -10,8 +10,9 @@
 @SuppressWarnings("unused")
 public final class TableInNestedNS extends Table {
   public static TableInNestedNS getRootAsTableInNestedNS(ByteBuffer _bb) { return getRootAsTableInNestedNS(_bb, new TableInNestedNS()); }
-  public static TableInNestedNS getRootAsTableInNestedNS(ByteBuffer _bb, TableInNestedNS obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
-  public TableInNestedNS __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TableInNestedNS getRootAsTableInNestedNS(ByteBuffer _bb, TableInNestedNS obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public TableInNestedNS __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public int foo() { int o = __offset(4); return o != 0 ? bb.getInt(o + bb_pos) : 0; }
   public boolean mutateFoo(int foo) { int o = __offset(4); if (o != 0) { bb.putInt(o + bb_pos, foo); return true; } else { return false; } }
diff --git a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.py b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.py
index e8e1f2b..d6d1674 100644
--- a/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.py
+++ b/tests/namespace_test/NamespaceA/NamespaceB/TableInNestedNS.py
@@ -7,6 +7,13 @@
 class TableInNestedNS(object):
     __slots__ = ['_tab']
 
+    @classmethod
+    def GetRootAsTableInNestedNS(cls, buf, offset):
+        n = flatbuffers.encode.Get(flatbuffers.packer.uoffset, buf, offset)
+        x = TableInNestedNS()
+        x.Init(buf, n + offset)
+        return x
+
     # TableInNestedNS
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/namespace_test/NamespaceA/SecondTableInA.cs b/tests/namespace_test/NamespaceA/SecondTableInA.cs
index 96ae378..2048828 100644
--- a/tests/namespace_test/NamespaceA/SecondTableInA.cs
+++ b/tests/namespace_test/NamespaceA/SecondTableInA.cs
@@ -6,13 +6,16 @@
 using System;
 using FlatBuffers;
 
-public sealed class SecondTableInA : Table {
+public struct SecondTableInA : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static SecondTableInA GetRootAsSecondTableInA(ByteBuffer _bb) { return GetRootAsSecondTableInA(_bb, new SecondTableInA()); }
-  public static SecondTableInA GetRootAsSecondTableInA(ByteBuffer _bb, SecondTableInA obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public SecondTableInA __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static SecondTableInA GetRootAsSecondTableInA(ByteBuffer _bb, SecondTableInA obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public SecondTableInA __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public NamespaceC.TableInC ReferToC { get { return GetReferToC(new NamespaceC.TableInC()); } }
-  public NamespaceC.TableInC GetReferToC(NamespaceC.TableInC obj) { int o = __offset(4); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
+  public NamespaceC.TableInC? ReferToC { get { int o = __p.__offset(4); return o != 0 ? (NamespaceC.TableInC?)(new NamespaceC.TableInC()).__assign(__p.__indirect(o + __p.bb_pos), __p.bb) : null; } }
 
   public static Offset<SecondTableInA> CreateSecondTableInA(FlatBufferBuilder builder,
       Offset<NamespaceC.TableInC> refer_to_cOffset = default(Offset<NamespaceC.TableInC>)) {
diff --git a/tests/namespace_test/NamespaceA/SecondTableInA.go b/tests/namespace_test/NamespaceA/SecondTableInA.go
index efc7713..f53a1ea 100644
--- a/tests/namespace_test/NamespaceA/SecondTableInA.go
+++ b/tests/namespace_test/NamespaceA/SecondTableInA.go
@@ -5,10 +5,18 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type SecondTableInA struct {
 	_tab flatbuffers.Table
 }
 
+func GetRootAsSecondTableInA(buf []byte, offset flatbuffers.UOffsetT) *SecondTableInA {
+	n := flatbuffers.GetUOffsetT(buf[offset:])
+	x := &SecondTableInA{}
+	x.Init(buf, n+offset)
+	return x
+}
+
 func (rcv *SecondTableInA) Init(buf []byte, i flatbuffers.UOffsetT) {
 	rcv._tab.Bytes = buf
 	rcv._tab.Pos = i
@@ -27,6 +35,12 @@
 	return nil
 }
 
-func SecondTableInAStart(builder *flatbuffers.Builder) { builder.StartObject(1) }
-func SecondTableInAAddReferToC(builder *flatbuffers.Builder, referToC flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(referToC), 0) }
-func SecondTableInAEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func SecondTableInAStart(builder *flatbuffers.Builder) {
+	builder.StartObject(1)
+}
+func SecondTableInAAddReferToC(builder *flatbuffers.Builder, referToC flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(referToC), 0)
+}
+func SecondTableInAEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/namespace_test/NamespaceA/SecondTableInA.java b/tests/namespace_test/NamespaceA/SecondTableInA.java
index e6f390a..7c56b88 100644
--- a/tests/namespace_test/NamespaceA/SecondTableInA.java
+++ b/tests/namespace_test/NamespaceA/SecondTableInA.java
@@ -10,11 +10,12 @@
 @SuppressWarnings("unused")
 public final class SecondTableInA extends Table {
   public static SecondTableInA getRootAsSecondTableInA(ByteBuffer _bb) { return getRootAsSecondTableInA(_bb, new SecondTableInA()); }
-  public static SecondTableInA getRootAsSecondTableInA(ByteBuffer _bb, SecondTableInA obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
-  public SecondTableInA __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static SecondTableInA getRootAsSecondTableInA(ByteBuffer _bb, SecondTableInA obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public SecondTableInA __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public NamespaceC.TableInC referToC() { return referToC(new NamespaceC.TableInC()); }
-  public NamespaceC.TableInC referToC(NamespaceC.TableInC obj) { int o = __offset(4); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
+  public NamespaceC.TableInC referToC(NamespaceC.TableInC obj) { int o = __offset(4); return o != 0 ? obj.__assign(__indirect(o + bb_pos), bb) : null; }
 
   public static int createSecondTableInA(FlatBufferBuilder builder,
       int refer_to_cOffset) {
diff --git a/tests/namespace_test/NamespaceA/SecondTableInA.py b/tests/namespace_test/NamespaceA/SecondTableInA.py
index ab11701..20dac3e 100644
--- a/tests/namespace_test/NamespaceA/SecondTableInA.py
+++ b/tests/namespace_test/NamespaceA/SecondTableInA.py
@@ -7,6 +7,13 @@
 class SecondTableInA(object):
     __slots__ = ['_tab']
 
+    @classmethod
+    def GetRootAsSecondTableInA(cls, buf, offset):
+        n = flatbuffers.encode.Get(flatbuffers.packer.uoffset, buf, offset)
+        x = SecondTableInA()
+        x.Init(buf, n + offset)
+        return x
+
     # SecondTableInA
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/namespace_test/NamespaceA/TableInFirstNS.cs b/tests/namespace_test/NamespaceA/TableInFirstNS.cs
index 4b4be11..3b5659a 100644
--- a/tests/namespace_test/NamespaceA/TableInFirstNS.cs
+++ b/tests/namespace_test/NamespaceA/TableInFirstNS.cs
@@ -6,25 +6,27 @@
 using System;
 using FlatBuffers;
 
-public sealed class TableInFirstNS : Table {
+public struct TableInFirstNS : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static TableInFirstNS GetRootAsTableInFirstNS(ByteBuffer _bb) { return GetRootAsTableInFirstNS(_bb, new TableInFirstNS()); }
-  public static TableInFirstNS GetRootAsTableInFirstNS(ByteBuffer _bb, TableInFirstNS obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public TableInFirstNS __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TableInFirstNS GetRootAsTableInFirstNS(ByteBuffer _bb, TableInFirstNS obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public TableInFirstNS __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public NamespaceA.NamespaceB.TableInNestedNS FooTable { get { return GetFooTable(new NamespaceA.NamespaceB.TableInNestedNS()); } }
-  public NamespaceA.NamespaceB.TableInNestedNS GetFooTable(NamespaceA.NamespaceB.TableInNestedNS obj) { int o = __offset(4); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
-  public NamespaceA.NamespaceB.EnumInNestedNS FooEnum { get { int o = __offset(6); return o != 0 ? (NamespaceA.NamespaceB.EnumInNestedNS)bb.GetSbyte(o + bb_pos) : NamespaceA.NamespaceB.EnumInNestedNS.A; } }
-  public bool MutateFooEnum(NamespaceA.NamespaceB.EnumInNestedNS foo_enum) { int o = __offset(6); if (o != 0) { bb.PutSbyte(o + bb_pos, (sbyte)foo_enum); return true; } else { return false; } }
-  public NamespaceA.NamespaceB.StructInNestedNS FooStruct { get { return GetFooStruct(new NamespaceA.NamespaceB.StructInNestedNS()); } }
-  public NamespaceA.NamespaceB.StructInNestedNS GetFooStruct(NamespaceA.NamespaceB.StructInNestedNS obj) { int o = __offset(8); return o != 0 ? obj.__init(o + bb_pos, bb) : null; }
+  public NamespaceA.NamespaceB.TableInNestedNS? FooTable { get { int o = __p.__offset(4); return o != 0 ? (NamespaceA.NamespaceB.TableInNestedNS?)(new NamespaceA.NamespaceB.TableInNestedNS()).__assign(__p.__indirect(o + __p.bb_pos), __p.bb) : null; } }
+  public NamespaceA.NamespaceB.EnumInNestedNS FooEnum { get { int o = __p.__offset(6); return o != 0 ? (NamespaceA.NamespaceB.EnumInNestedNS)__p.bb.GetSbyte(o + __p.bb_pos) : NamespaceA.NamespaceB.EnumInNestedNS.A; } }
+  public bool MutateFooEnum(NamespaceA.NamespaceB.EnumInNestedNS foo_enum) { int o = __p.__offset(6); if (o != 0) { __p.bb.PutSbyte(o + __p.bb_pos, (sbyte)foo_enum); return true; } else { return false; } }
+  public NamespaceA.NamespaceB.StructInNestedNS? FooStruct { get { int o = __p.__offset(8); return o != 0 ? (NamespaceA.NamespaceB.StructInNestedNS?)(new NamespaceA.NamespaceB.StructInNestedNS()).__assign(o + __p.bb_pos, __p.bb) : null; } }
 
   public static void StartTableInFirstNS(FlatBufferBuilder builder) { builder.StartObject(3); }
   public static void AddFooTable(FlatBufferBuilder builder, Offset<NamespaceA.NamespaceB.TableInNestedNS> fooTableOffset) { builder.AddOffset(0, fooTableOffset.Value, 0); }
   public static void AddFooEnum(FlatBufferBuilder builder, NamespaceA.NamespaceB.EnumInNestedNS fooEnum) { builder.AddSbyte(1, (sbyte)fooEnum, 0); }
   public static void AddFooStruct(FlatBufferBuilder builder, Offset<NamespaceA.NamespaceB.StructInNestedNS> fooStructOffset) { builder.AddStruct(2, fooStructOffset.Value, 0); }
-  public static Offset<NamespaceA.TableInFirstNS> EndTableInFirstNS(FlatBufferBuilder builder) {
+  public static Offset<TableInFirstNS> EndTableInFirstNS(FlatBufferBuilder builder) {
     int o = builder.EndObject();
-    return new Offset<NamespaceA.TableInFirstNS>(o);
+    return new Offset<TableInFirstNS>(o);
   }
 };
 
diff --git a/tests/namespace_test/NamespaceA/TableInFirstNS.go b/tests/namespace_test/NamespaceA/TableInFirstNS.go
index 5580d5d..4820a8a 100644
--- a/tests/namespace_test/NamespaceA/TableInFirstNS.go
+++ b/tests/namespace_test/NamespaceA/TableInFirstNS.go
@@ -5,10 +5,18 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type TableInFirstNS struct {
 	_tab flatbuffers.Table
 }
 
+func GetRootAsTableInFirstNS(buf []byte, offset flatbuffers.UOffsetT) *TableInFirstNS {
+	n := flatbuffers.GetUOffsetT(buf[offset:])
+	x := &TableInFirstNS{}
+	x.Init(buf, n+offset)
+	return x
+}
+
 func (rcv *TableInFirstNS) Init(buf []byte, i flatbuffers.UOffsetT) {
 	rcv._tab.Bytes = buf
 	rcv._tab.Pos = i
@@ -35,6 +43,10 @@
 	return 0
 }
 
+func (rcv *TableInFirstNS) MutateFooEnum(n int8) bool {
+	return rcv._tab.MutateInt8Slot(6, n)
+}
+
 func (rcv *TableInFirstNS) FooStruct(obj *StructInNestedNS) *StructInNestedNS {
 	o := flatbuffers.UOffsetT(rcv._tab.Offset(8))
 	if o != 0 {
@@ -48,8 +60,18 @@
 	return nil
 }
 
-func TableInFirstNSStart(builder *flatbuffers.Builder) { builder.StartObject(3) }
-func TableInFirstNSAddFooTable(builder *flatbuffers.Builder, fooTable flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(fooTable), 0) }
-func TableInFirstNSAddFooEnum(builder *flatbuffers.Builder, fooEnum int8) { builder.PrependInt8Slot(1, fooEnum, 0) }
-func TableInFirstNSAddFooStruct(builder *flatbuffers.Builder, fooStruct flatbuffers.UOffsetT) { builder.PrependStructSlot(2, flatbuffers.UOffsetT(fooStruct), 0) }
-func TableInFirstNSEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func TableInFirstNSStart(builder *flatbuffers.Builder) {
+	builder.StartObject(3)
+}
+func TableInFirstNSAddFooTable(builder *flatbuffers.Builder, fooTable flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(fooTable), 0)
+}
+func TableInFirstNSAddFooEnum(builder *flatbuffers.Builder, fooEnum int8) {
+	builder.PrependInt8Slot(1, fooEnum, 0)
+}
+func TableInFirstNSAddFooStruct(builder *flatbuffers.Builder, fooStruct flatbuffers.UOffsetT) {
+	builder.PrependStructSlot(2, flatbuffers.UOffsetT(fooStruct), 0)
+}
+func TableInFirstNSEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/namespace_test/NamespaceA/TableInFirstNS.java b/tests/namespace_test/NamespaceA/TableInFirstNS.java
index b44df97..b03c462 100644
--- a/tests/namespace_test/NamespaceA/TableInFirstNS.java
+++ b/tests/namespace_test/NamespaceA/TableInFirstNS.java
@@ -10,15 +10,16 @@
 @SuppressWarnings("unused")
 public final class TableInFirstNS extends Table {
   public static TableInFirstNS getRootAsTableInFirstNS(ByteBuffer _bb) { return getRootAsTableInFirstNS(_bb, new TableInFirstNS()); }
-  public static TableInFirstNS getRootAsTableInFirstNS(ByteBuffer _bb, TableInFirstNS obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
-  public TableInFirstNS __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TableInFirstNS getRootAsTableInFirstNS(ByteBuffer _bb, TableInFirstNS obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public TableInFirstNS __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public NamespaceA.NamespaceB.TableInNestedNS fooTable() { return fooTable(new NamespaceA.NamespaceB.TableInNestedNS()); }
-  public NamespaceA.NamespaceB.TableInNestedNS fooTable(NamespaceA.NamespaceB.TableInNestedNS obj) { int o = __offset(4); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
+  public NamespaceA.NamespaceB.TableInNestedNS fooTable(NamespaceA.NamespaceB.TableInNestedNS obj) { int o = __offset(4); return o != 0 ? obj.__assign(__indirect(o + bb_pos), bb) : null; }
   public byte fooEnum() { int o = __offset(6); return o != 0 ? bb.get(o + bb_pos) : 0; }
   public boolean mutateFooEnum(byte foo_enum) { int o = __offset(6); if (o != 0) { bb.put(o + bb_pos, foo_enum); return true; } else { return false; } }
   public NamespaceA.NamespaceB.StructInNestedNS fooStruct() { return fooStruct(new NamespaceA.NamespaceB.StructInNestedNS()); }
-  public NamespaceA.NamespaceB.StructInNestedNS fooStruct(NamespaceA.NamespaceB.StructInNestedNS obj) { int o = __offset(8); return o != 0 ? obj.__init(o + bb_pos, bb) : null; }
+  public NamespaceA.NamespaceB.StructInNestedNS fooStruct(NamespaceA.NamespaceB.StructInNestedNS obj) { int o = __offset(8); return o != 0 ? obj.__assign(o + bb_pos, bb) : null; }
 
   public static void startTableInFirstNS(FlatBufferBuilder builder) { builder.startObject(3); }
   public static void addFooTable(FlatBufferBuilder builder, int fooTableOffset) { builder.addOffset(0, fooTableOffset, 0); }
diff --git a/tests/namespace_test/NamespaceA/TableInFirstNS.py b/tests/namespace_test/NamespaceA/TableInFirstNS.py
index 3a652f4..40cbeba 100644
--- a/tests/namespace_test/NamespaceA/TableInFirstNS.py
+++ b/tests/namespace_test/NamespaceA/TableInFirstNS.py
@@ -7,6 +7,13 @@
 class TableInFirstNS(object):
     __slots__ = ['_tab']
 
+    @classmethod
+    def GetRootAsTableInFirstNS(cls, buf, offset):
+        n = flatbuffers.encode.Get(flatbuffers.packer.uoffset, buf, offset)
+        x = TableInFirstNS()
+        x.Init(buf, n + offset)
+        return x
+
     # TableInFirstNS
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/namespace_test/NamespaceC/TableInC.cs b/tests/namespace_test/NamespaceC/TableInC.cs
index 0f75dfe..fa53ec5 100644
--- a/tests/namespace_test/NamespaceC/TableInC.cs
+++ b/tests/namespace_test/NamespaceC/TableInC.cs
@@ -6,19 +6,21 @@
 using System;
 using FlatBuffers;
 
-public sealed class TableInC : Table {
+public struct TableInC : IFlatbufferObject
+{
+  private Table __p;
+  public ByteBuffer ByteBuffer { get { return __p.bb; } }
   public static TableInC GetRootAsTableInC(ByteBuffer _bb) { return GetRootAsTableInC(_bb, new TableInC()); }
-  public static TableInC GetRootAsTableInC(ByteBuffer _bb, TableInC obj) { return (obj.__init(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
-  public TableInC __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TableInC GetRootAsTableInC(ByteBuffer _bb, TableInC obj) { return (obj.__assign(_bb.GetInt(_bb.Position) + _bb.Position, _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { __p.bb_pos = _i; __p.bb = _bb; }
+  public TableInC __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
-  public NamespaceA.TableInFirstNS ReferToA1 { get { return GetReferToA1(new NamespaceA.TableInFirstNS()); } }
-  public NamespaceA.TableInFirstNS GetReferToA1(NamespaceA.TableInFirstNS obj) { int o = __offset(4); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
-  public SecondTableInA ReferToA2 { get { return GetReferToA2(new SecondTableInA()); } }
-  public SecondTableInA GetReferToA2(SecondTableInA obj) { int o = __offset(6); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
+  public NamespaceA.TableInFirstNS? ReferToA1 { get { int o = __p.__offset(4); return o != 0 ? (NamespaceA.TableInFirstNS?)(new NamespaceA.TableInFirstNS()).__assign(__p.__indirect(o + __p.bb_pos), __p.bb) : null; } }
+  public NamespaceA.SecondTableInA? ReferToA2 { get { int o = __p.__offset(6); return o != 0 ? (NamespaceA.SecondTableInA?)(new NamespaceA.SecondTableInA()).__assign(__p.__indirect(o + __p.bb_pos), __p.bb) : null; } }
 
-  public static Offset<NamespaceC.TableInC> CreateTableInC(FlatBufferBuilder builder,
+  public static Offset<TableInC> CreateTableInC(FlatBufferBuilder builder,
       Offset<NamespaceA.TableInFirstNS> refer_to_a1Offset = default(Offset<NamespaceA.TableInFirstNS>),
-      Offset<SecondTableInA> refer_to_a2Offset = default(Offset<SecondTableInA>)) {
+      Offset<NamespaceA.SecondTableInA> refer_to_a2Offset = default(Offset<NamespaceA.SecondTableInA>)) {
     builder.StartObject(2);
     TableInC.AddReferToA2(builder, refer_to_a2Offset);
     TableInC.AddReferToA1(builder, refer_to_a1Offset);
@@ -27,10 +29,10 @@
 
   public static void StartTableInC(FlatBufferBuilder builder) { builder.StartObject(2); }
   public static void AddReferToA1(FlatBufferBuilder builder, Offset<NamespaceA.TableInFirstNS> referToA1Offset) { builder.AddOffset(0, referToA1Offset.Value, 0); }
-  public static void AddReferToA2(FlatBufferBuilder builder, Offset<SecondTableInA> referToA2Offset) { builder.AddOffset(1, referToA2Offset.Value, 0); }
-  public static Offset<NamespaceC.TableInC> EndTableInC(FlatBufferBuilder builder) {
+  public static void AddReferToA2(FlatBufferBuilder builder, Offset<NamespaceA.SecondTableInA> referToA2Offset) { builder.AddOffset(1, referToA2Offset.Value, 0); }
+  public static Offset<TableInC> EndTableInC(FlatBufferBuilder builder) {
     int o = builder.EndObject();
-    return new Offset<NamespaceC.TableInC>(o);
+    return new Offset<TableInC>(o);
   }
 };
 
diff --git a/tests/namespace_test/NamespaceC/TableInC.go b/tests/namespace_test/NamespaceC/TableInC.go
index dc75c45..d0d8b00 100644
--- a/tests/namespace_test/NamespaceC/TableInC.go
+++ b/tests/namespace_test/NamespaceC/TableInC.go
@@ -5,10 +5,18 @@
 import (
 	flatbuffers "github.com/google/flatbuffers/go"
 )
+
 type TableInC struct {
 	_tab flatbuffers.Table
 }
 
+func GetRootAsTableInC(buf []byte, offset flatbuffers.UOffsetT) *TableInC {
+	n := flatbuffers.GetUOffsetT(buf[offset:])
+	x := &TableInC{}
+	x.Init(buf, n+offset)
+	return x
+}
+
 func (rcv *TableInC) Init(buf []byte, i flatbuffers.UOffsetT) {
 	rcv._tab.Bytes = buf
 	rcv._tab.Pos = i
@@ -40,7 +48,15 @@
 	return nil
 }
 
-func TableInCStart(builder *flatbuffers.Builder) { builder.StartObject(2) }
-func TableInCAddReferToA1(builder *flatbuffers.Builder, referToA1 flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(referToA1), 0) }
-func TableInCAddReferToA2(builder *flatbuffers.Builder, referToA2 flatbuffers.UOffsetT) { builder.PrependUOffsetTSlot(1, flatbuffers.UOffsetT(referToA2), 0) }
-func TableInCEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT { return builder.EndObject() }
+func TableInCStart(builder *flatbuffers.Builder) {
+	builder.StartObject(2)
+}
+func TableInCAddReferToA1(builder *flatbuffers.Builder, referToA1 flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(0, flatbuffers.UOffsetT(referToA1), 0)
+}
+func TableInCAddReferToA2(builder *flatbuffers.Builder, referToA2 flatbuffers.UOffsetT) {
+	builder.PrependUOffsetTSlot(1, flatbuffers.UOffsetT(referToA2), 0)
+}
+func TableInCEnd(builder *flatbuffers.Builder) flatbuffers.UOffsetT {
+	return builder.EndObject()
+}
diff --git a/tests/namespace_test/NamespaceC/TableInC.java b/tests/namespace_test/NamespaceC/TableInC.java
index 19bb4cd..56d4954 100644
--- a/tests/namespace_test/NamespaceC/TableInC.java
+++ b/tests/namespace_test/NamespaceC/TableInC.java
@@ -10,13 +10,14 @@
 @SuppressWarnings("unused")
 public final class TableInC extends Table {
   public static TableInC getRootAsTableInC(ByteBuffer _bb) { return getRootAsTableInC(_bb, new TableInC()); }
-  public static TableInC getRootAsTableInC(ByteBuffer _bb, TableInC obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__init(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
-  public TableInC __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; return this; }
+  public static TableInC getRootAsTableInC(ByteBuffer _bb, TableInC obj) { _bb.order(ByteOrder.LITTLE_ENDIAN); return (obj.__assign(_bb.getInt(_bb.position()) + _bb.position(), _bb)); }
+  public void __init(int _i, ByteBuffer _bb) { bb_pos = _i; bb = _bb; }
+  public TableInC __assign(int _i, ByteBuffer _bb) { __init(_i, _bb); return this; }
 
   public NamespaceA.TableInFirstNS referToA1() { return referToA1(new NamespaceA.TableInFirstNS()); }
-  public NamespaceA.TableInFirstNS referToA1(NamespaceA.TableInFirstNS obj) { int o = __offset(4); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
-  public SecondTableInA referToA2() { return referToA2(new SecondTableInA()); }
-  public SecondTableInA referToA2(SecondTableInA obj) { int o = __offset(6); return o != 0 ? obj.__init(__indirect(o + bb_pos), bb) : null; }
+  public NamespaceA.TableInFirstNS referToA1(NamespaceA.TableInFirstNS obj) { int o = __offset(4); return o != 0 ? obj.__assign(__indirect(o + bb_pos), bb) : null; }
+  public NamespaceA.SecondTableInA referToA2() { return referToA2(new NamespaceA.SecondTableInA()); }
+  public NamespaceA.SecondTableInA referToA2(NamespaceA.SecondTableInA obj) { int o = __offset(6); return o != 0 ? obj.__assign(__indirect(o + bb_pos), bb) : null; }
 
   public static int createTableInC(FlatBufferBuilder builder,
       int refer_to_a1Offset,
diff --git a/tests/namespace_test/NamespaceC/TableInC.py b/tests/namespace_test/NamespaceC/TableInC.py
index 5a4376e..90b8736 100644
--- a/tests/namespace_test/NamespaceC/TableInC.py
+++ b/tests/namespace_test/NamespaceC/TableInC.py
@@ -7,6 +7,13 @@
 class TableInC(object):
     __slots__ = ['_tab']
 
+    @classmethod
+    def GetRootAsTableInC(cls, buf, offset):
+        n = flatbuffers.encode.Get(flatbuffers.packer.uoffset, buf, offset)
+        x = TableInC()
+        x.Init(buf, n + offset)
+        return x
+
     # TableInC
     def Init(self, buf, pos):
         self._tab = flatbuffers.table.Table(buf, pos)
diff --git a/tests/namespace_test/namespace_test1_generated.h b/tests/namespace_test/namespace_test1_generated.h
index 23a0964..59d4030 100644
--- a/tests/namespace_test/namespace_test1_generated.h
+++ b/tests/namespace_test/namespace_test1_generated.h
@@ -33,6 +33,8 @@
   int32_t b_;
 
  public:
+  StructInNestedNS() { memset(this, 0, sizeof(StructInNestedNS)); }
+  StructInNestedNS(const StructInNestedNS &_o) { memcpy(this, &_o, sizeof(StructInNestedNS)); }
   StructInNestedNS(int32_t _a, int32_t _b)
     : a_(flatbuffers::EndianScalar(_a)), b_(flatbuffers::EndianScalar(_b)) { }
 
diff --git a/tests/namespace_test/namespace_test1_generated.js b/tests/namespace_test/namespace_test1_generated.js
index 769b523..7551a18 100644
--- a/tests/namespace_test/namespace_test1_generated.js
+++ b/tests/namespace_test/namespace_test1_generated.js
@@ -2,12 +2,14 @@
 
 /**
  * @const
-*/
+ * @namespace
+ */
 var NamespaceA = NamespaceA || {};
 
 /**
  * @const
-*/
+ * @namespace
+ */
 NamespaceA.NamespaceB = NamespaceA.NamespaceB || {};
 
 /**
@@ -63,6 +65,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+NamespaceA.NamespaceB.TableInNestedNS.prototype.mutate_foo = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 4);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {flatbuffers.Builder} builder
  */
 NamespaceA.NamespaceB.TableInNestedNS.startTableInNestedNS = function(builder) {
@@ -120,6 +137,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+NamespaceA.NamespaceB.StructInNestedNS.prototype.mutate_a = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 0);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @returns {number}
  */
 NamespaceA.NamespaceB.StructInNestedNS.prototype.b = function() {
@@ -127,6 +159,21 @@
 };
 
 /**
+ * @param {number} value
+ * @returns {boolean}
+ */
+NamespaceA.NamespaceB.StructInNestedNS.prototype.mutate_b = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 4);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt32(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {flatbuffers.Builder} builder
  * @param {number} a
  * @param {number} b
diff --git a/tests/namespace_test/namespace_test2_generated.h b/tests/namespace_test/namespace_test2_generated.h
index 885eae2..77578bc 100644
--- a/tests/namespace_test/namespace_test2_generated.h
+++ b/tests/namespace_test/namespace_test2_generated.h
@@ -154,4 +154,12 @@
 
 }  // namespace NamespaceA
 
+namespace NamespaceC {
+
+}  // namespace NamespaceC
+
+namespace NamespaceA {
+
+}  // namespace NamespaceA
+
 #endif  // FLATBUFFERS_GENERATED_NAMESPACETEST2_NAMESPACEA_H_
diff --git a/tests/namespace_test/namespace_test2_generated.js b/tests/namespace_test/namespace_test2_generated.js
index c195370..c1c25ef 100644
--- a/tests/namespace_test/namespace_test2_generated.js
+++ b/tests/namespace_test/namespace_test2_generated.js
@@ -2,17 +2,20 @@
 
 /**
  * @const
-*/
+ * @namespace
+ */
 var NamespaceA = NamespaceA || {};
 
 /**
  * @const
-*/
+ * @namespace
+ */
 NamespaceA.NamespaceB = NamespaceA.NamespaceB || {};
 
 /**
  * @const
-*/
+ * @namespace
+ */
 var NamespaceC = NamespaceC || {};
 
 /**
@@ -68,6 +71,21 @@
 };
 
 /**
+ * @param {NamespaceA.NamespaceB.EnumInNestedNS} value
+ * @returns {boolean}
+ */
+NamespaceA.TableInFirstNS.prototype.mutate_foo_enum = function(value) {
+  var offset = this.bb.__offset(this.bb_pos, 6);
+
+  if (offset === 0) {
+    return false;
+  }
+
+  this.bb.writeInt8(this.bb_pos + offset, value);
+  return true;
+};
+
+/**
  * @param {NamespaceA.NamespaceB.StructInNestedNS=} obj
  * @returns {NamespaceA.NamespaceB.StructInNestedNS}
  */
diff --git a/tests/py_test.py b/tests/py_test.py
index 82f8390..e660944 100644
--- a/tests/py_test.py
+++ b/tests/py_test.py
@@ -1034,6 +1034,23 @@
         self.assertEqual(7, mon2.Testhashs64Fnv1a())
         self.assertEqual(8, mon2.Testhashu64Fnv1a())
 
+    def test_getrootas_for_nonroot_table(self):
+        b = flatbuffers.Builder(0)
+        string = b.CreateString("MyStat")
+
+        MyGame.Example.Stat.StatStart(b)
+        MyGame.Example.Stat.StatAddId(b, string)
+        MyGame.Example.Stat.StatAddVal(b, 12345678)
+        MyGame.Example.Stat.StatAddCount(b, 12345)
+        stat = MyGame.Example.Stat.StatEnd(b)
+        b.Finish(stat)
+
+        stat2 = MyGame.Example.Stat.Stat.GetRootAsStat(b.Bytes, b.Head())
+
+        self.assertEqual(b"MyStat", stat2.Id())
+        self.assertEqual(12345678, stat2.Val())
+        self.assertEqual(12345, stat2.Count())
+
 
 class TestVtableDeduplication(unittest.TestCase):
     ''' TestVtableDeduplication verifies that vtables are deduplicated. '''
diff --git a/tests/test.cpp b/tests/test.cpp
index 402843a..ab18354 100644
--- a/tests/test.cpp
+++ b/tests/test.cpp
@@ -25,7 +25,9 @@
 #include "namespace_test/namespace_test1_generated.h"
 #include "namespace_test/namespace_test2_generated.h"
 
-#include <random>
+#ifndef FLATBUFFERS_CPP98_STL
+  #include <random>
+#endif
 
 using namespace MyGame::Example;
 
@@ -124,7 +126,9 @@
   });
 
   // Creating vectors of strings in one convenient call.
-  std::vector<std::string> names2 = { "jane", "mary" };
+  std::vector<std::string> names2;
+  names2.push_back("jane");
+  names2.push_back("mary");
   auto vecofstrings2 = builder.CreateVectorOfStrings(names2);
 
   // Create an array of sorted tables, can be used with binary search when read:
@@ -155,7 +159,8 @@
 }
 
 //  example of accessing a buffer loaded in memory:
-void AccessFlatBufferTest(const uint8_t *flatbuf, size_t length) {
+void AccessFlatBufferTest(const uint8_t *flatbuf, size_t length,
+                          bool pooled = true) {
 
   // First, verify the buffers integrity (optional)
   flatbuffers::Verifier verifier(flatbuf, length);
@@ -218,9 +223,11 @@
   TEST_EQ(vecofstrings->Length(), 4U);
   TEST_EQ_STR(vecofstrings->Get(0)->c_str(), "bob");
   TEST_EQ_STR(vecofstrings->Get(1)->c_str(), "fred");
-  // These should have pointer equality because of string pooling.
-  TEST_EQ(vecofstrings->Get(0)->c_str(), vecofstrings->Get(2)->c_str());
-  TEST_EQ(vecofstrings->Get(1)->c_str(), vecofstrings->Get(3)->c_str());
+  if (pooled) {
+    // These should have pointer equality because of string pooling.
+    TEST_EQ(vecofstrings->Get(0)->c_str(), vecofstrings->Get(2)->c_str());
+    TEST_EQ(vecofstrings->Get(1)->c_str(), vecofstrings->Get(3)->c_str());
+  }
 
   auto vecofstrings2 = monster->testarrayofstring2();
   if (vecofstrings2) {
@@ -263,6 +270,9 @@
   // Checking for presence of fields:
   TEST_EQ(flatbuffers::IsFieldPresent(monster, Monster::VT_HP), true);
   TEST_EQ(flatbuffers::IsFieldPresent(monster, Monster::VT_MANA), false);
+
+  // Obtaining a buffer from a root:
+  TEST_EQ(GetBufferStartFromRootPointer(monster), flatbuf);
 }
 
 // Change a FlatBuffer in-place, after it has been constructed.
@@ -305,6 +315,113 @@
   AccessFlatBufferTest(flatbuf, length);
 }
 
+// Unpack a FlatBuffer into objects.
+void ObjectFlatBuffersTest(uint8_t *flatbuf) {
+  // Optional: we can specify resolver and rehasher functions to turn hashed
+  // strings into object pointers and back, to implement remote references
+  // and such.
+  auto resolver = flatbuffers::resolver_function_t(
+                    [](void **pointer_adr, flatbuffers::hash_value_t hash) {
+    (void)pointer_adr;
+    (void)hash;
+    // Don't actually do anything, leave variable null.
+  });
+  auto rehasher = flatbuffers::rehasher_function_t(
+                    [](void *pointer) -> flatbuffers::hash_value_t {
+    (void)pointer;
+    return 0;
+  });
+
+  // Turn a buffer into C++ objects.
+  auto monster1 = UnPackMonster(flatbuf, &resolver);
+
+  // Re-serialize the data.
+  flatbuffers::FlatBufferBuilder fbb1;
+  fbb1.Finish(CreateMonster(fbb1, monster1.get(), &rehasher),
+              MonsterIdentifier());
+
+  // Unpack again, and re-serialize again.
+  auto monster2 = UnPackMonster(fbb1.GetBufferPointer(), &resolver);
+  flatbuffers::FlatBufferBuilder fbb2;
+  fbb2.Finish(CreateMonster(fbb2, monster2.get(), &rehasher),
+              MonsterIdentifier());
+
+  // Now we've gone full round-trip, the two buffers should match.
+  auto len1 = fbb1.GetSize();
+  auto len2 = fbb2.GetSize();
+  TEST_EQ(len1, len2);
+  TEST_EQ(memcmp(fbb1.GetBufferPointer(), fbb2.GetBufferPointer(),
+                 len1), 0);
+
+  // Test it with the original buffer test to make sure all data survived.
+  AccessFlatBufferTest(fbb2.GetBufferPointer(), len2, false);
+
+  // Test accessing fields, similar to AccessFlatBufferTest above.
+  TEST_EQ(monster2->hp, 80);
+  TEST_EQ(monster2->mana, 150);  // default
+  TEST_EQ_STR(monster2->name.c_str(), "MyMonster");
+
+  auto &pos = monster2->pos;
+  TEST_NOTNULL(pos);
+  TEST_EQ(pos->z(), 3);
+  TEST_EQ(pos->test3().a(), 10);
+  TEST_EQ(pos->test3().b(), 20);
+
+  auto &inventory = monster2->inventory;
+  TEST_EQ(inventory.size(), 10UL);
+  unsigned char inv_data[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
+  for (auto it = inventory.begin(); it != inventory.end(); ++it)
+    TEST_EQ(*it, inv_data[it - inventory.begin()]);
+
+  TEST_EQ(monster2->color, Color_Blue);
+
+  auto monster3 = monster2->test.AsMonster();
+  TEST_NOTNULL(monster3);
+  TEST_EQ_STR(monster3->name.c_str(), "Fred");
+
+  auto &vecofstrings = monster2->testarrayofstring;
+  TEST_EQ(vecofstrings.size(), 4U);
+  TEST_EQ_STR(vecofstrings[0].c_str(), "bob");
+  TEST_EQ_STR(vecofstrings[1].c_str(), "fred");
+
+  auto &vecofstrings2 = monster2->testarrayofstring2;
+  TEST_EQ(vecofstrings2.size(), 2U);
+  TEST_EQ_STR(vecofstrings2[0].c_str(), "jane");
+  TEST_EQ_STR(vecofstrings2[1].c_str(), "mary");
+
+  auto &vecoftables = monster2->testarrayoftables;
+  TEST_EQ(vecoftables.size(), 3U);
+  TEST_EQ_STR(vecoftables[0]->name.c_str(), "Barney");
+  TEST_EQ(vecoftables[0]->hp, 1000);
+  TEST_EQ_STR(vecoftables[1]->name.c_str(), "Fred");
+  TEST_EQ_STR(vecoftables[2]->name.c_str(), "Wilma");
+
+  auto &tests = monster2->test4;
+  TEST_EQ(tests[0].a(), 10);
+  TEST_EQ(tests[0].b(), 20);
+  TEST_EQ(tests[1].a(), 30);
+  TEST_EQ(tests[1].b(), 40);
+}
+
+// Prefix a FlatBuffer with a size field.
+void SizePrefixedTest() {
+  // Create size prefixed buffer.
+  flatbuffers::FlatBufferBuilder fbb;
+  fbb.FinishSizePrefixed(CreateMonster(fbb, 0, 200, 300,
+                                       fbb.CreateString("bob")));
+
+  // Verify it.
+  flatbuffers::Verifier verifier(fbb.GetBufferPointer(), fbb.GetSize());
+  TEST_EQ(verifier.VerifySizePrefixedBuffer<Monster>(nullptr), true);
+
+  // Access it.
+  auto m = flatbuffers::GetSizePrefixedRoot<MyGame::Example::Monster>(
+                                                        fbb.GetBufferPointer());
+  TEST_EQ(m->mana(), 200);
+  TEST_EQ(m->hp(), 300);
+  TEST_EQ_STR(m->name()->c_str(), "bob");
+}
+
 // example of parsing text straight into a buffer, and generating
 // text back from it:
 void ParseAndGenerateTextTest() {
@@ -332,7 +449,8 @@
   // to ensure it is correct, we now generate text back from the binary,
   // and compare the two:
   std::string jsongen;
-  GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  auto result = GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  TEST_EQ(result, true);
 
   if (jsongen != jsonfile) {
     printf("%s----------------\n%s", jsongen.c_str(), jsonfile.c_str());
@@ -354,7 +472,7 @@
   // Make sure the schema is what we expect it to be.
   auto &schema = *reflection::GetSchema(bfbsfile.c_str());
   auto root_table = schema.root_table();
-  TEST_EQ_STR(root_table->name()->c_str(), "Monster");
+  TEST_EQ_STR(root_table->name()->c_str(), "MyGame.Example.Monster");
   auto fields = root_table->fields();
   auto hp_field_ptr = fields->LookupByKey("hp");
   TEST_NOTNULL(hp_field_ptr);
@@ -367,6 +485,14 @@
   TEST_NOTNULL(friendly_field_ptr->attributes());
   TEST_NOTNULL(friendly_field_ptr->attributes()->LookupByKey("priority"));
 
+  // Make sure the table index is what we expect it to be.
+  auto pos_field_ptr = fields->LookupByKey("pos");
+  TEST_NOTNULL(pos_field_ptr);
+  TEST_EQ(pos_field_ptr->type()->base_type(), reflection::Obj);
+  auto pos_table_ptr = schema.objects()->Get(pos_field_ptr->type()->index());
+  TEST_NOTNULL(pos_table_ptr);
+  TEST_EQ_STR(pos_table_ptr->name()->c_str(), "MyGame.Example.Vec3");
+
   // Now use it to dynamically access a buffer.
   auto &root = *flatbuffers::GetAnyRoot(flatbuf);
   auto hp = flatbuffers::GetFieldI<uint16_t>(root, hp_field);
@@ -749,7 +875,8 @@
 
   std::string jsongen;
   parser.opts.indent_step = 0;
-  GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  auto result = GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  TEST_EQ(result, true);
 
   if (jsongen != json) {
     // These strings are larger than a megabyte, so we show the bytes around
@@ -855,7 +982,7 @@
 
   // Test conversion functions.
   TEST_EQ(FloatCompare(TestValue<float>("{ Y:cos(rad(180)) }","float"), -1), true);
-  
+
   // Test negative hex constant.
   TEST_EQ(TestValue<int>("{ Y:-0x80 }","int") == -128, true);
 }
@@ -900,15 +1027,55 @@
 
 void UnicodeTest() {
   flatbuffers::Parser parser;
+  // Without setting allow_non_utf8 = true, we treat \x sequences as byte sequences
+  // which are then validated as UTF-8.
   TEST_EQ(parser.Parse("table T { F:string; }"
                        "root_type T;"
                        "{ F:\"\\u20AC\\u00A2\\u30E6\\u30FC\\u30B6\\u30FC"
-                       "\\u5225\\u30B5\\u30A4\\u30C8\\x01\\x80\" }"), true);
+                       "\\u5225\\u30B5\\u30A4\\u30C8\\xE2\\x82\\xAC\\u0080\\uD83D\\uDE0E\" }"),
+          true);
   std::string jsongen;
   parser.opts.indent_step = -1;
-  GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
-  TEST_EQ(jsongen == "{F: \"\\u20AC\\u00A2\\u30E6\\u30FC\\u30B6\\u30FC"
-                     "\\u5225\\u30B5\\u30A4\\u30C8\\x01\\x80\"}", true);
+  auto result = GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  TEST_EQ(result, true);
+  TEST_EQ(jsongen,
+          std::string(
+            "{F: \"\\u20AC\\u00A2\\u30E6\\u30FC\\u30B6\\u30FC"
+            "\\u5225\\u30B5\\u30A4\\u30C8\\u20AC\\u0080\\uD83D\\uDE0E\"}"));
+}
+
+void UnicodeTestAllowNonUTF8() {
+  flatbuffers::Parser parser;
+  parser.opts.allow_non_utf8 = true;
+  TEST_EQ(parser.Parse("table T { F:string; }"
+                       "root_type T;"
+                       "{ F:\"\\u20AC\\u00A2\\u30E6\\u30FC\\u30B6\\u30FC"
+                       "\\u5225\\u30B5\\u30A4\\u30C8\\x01\\x80\\u0080\\uD83D\\uDE0E\" }"), true);
+  std::string jsongen;
+  parser.opts.indent_step = -1;
+  auto result = GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  TEST_EQ(result, true);
+  TEST_EQ(jsongen,
+          std::string(
+            "{F: \"\\u20AC\\u00A2\\u30E6\\u30FC\\u30B6\\u30FC"
+            "\\u5225\\u30B5\\u30A4\\u30C8\\u0001\\x80\\u0080\\uD83D\\uDE0E\"}"));
+}
+
+void UnicodeTestGenerateTextFailsOnNonUTF8() {
+  flatbuffers::Parser parser;
+  // Allow non-UTF-8 initially to model what happens when we load a binary flatbuffer from disk
+  // which contains non-UTF-8 strings.
+  parser.opts.allow_non_utf8 = true;
+  TEST_EQ(parser.Parse("table T { F:string; }"
+                       "root_type T;"
+                       "{ F:\"\\u20AC\\u00A2\\u30E6\\u30FC\\u30B6\\u30FC"
+                       "\\u5225\\u30B5\\u30A4\\u30C8\\x01\\x80\\u0080\\uD83D\\uDE0E\" }"), true);
+  std::string jsongen;
+  parser.opts.indent_step = -1;
+  // Now, disallow non-UTF-8 (the default behavior) so GenerateText indicates failure.
+  parser.opts.allow_non_utf8 = false;
+  auto result = GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  TEST_EQ(result, false);
 }
 
 void UnicodeSurrogatesTest() {
@@ -949,6 +1116,96 @@
     "{ F:\"\\uDC00\"}", "unpaired low surrogate");
 }
 
+void InvalidUTF8Test() {
+  // "1 byte" pattern, under min length of 2 bytes
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\x80\"}", "illegal UTF-8 sequence");
+  // 2 byte pattern, string too short
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xDF\"}", "illegal UTF-8 sequence");
+  // 3 byte pattern, string too short
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xEF\xBF\"}", "illegal UTF-8 sequence");
+  // 4 byte pattern, string too short
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xF7\xBF\xBF\"}", "illegal UTF-8 sequence");
+  // "5 byte" pattern, string too short
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xFB\xBF\xBF\xBF\"}", "illegal UTF-8 sequence");
+  // "6 byte" pattern, string too short
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xFD\xBF\xBF\xBF\xBF\"}", "illegal UTF-8 sequence");
+  // "7 byte" pattern, string too short
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xFE\xBF\xBF\xBF\xBF\xBF\"}", "illegal UTF-8 sequence");
+  // "5 byte" pattern, over max length of 4 bytes
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xFB\xBF\xBF\xBF\xBF\"}", "illegal UTF-8 sequence");
+  // "6 byte" pattern, over max length of 4 bytes
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xFD\xBF\xBF\xBF\xBF\xBF\"}", "illegal UTF-8 sequence");
+  // "7 byte" pattern, over max length of 4 bytes
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xFE\xBF\xBF\xBF\xBF\xBF\xBF\"}", "illegal UTF-8 sequence");
+
+  // Three invalid encodings for U+000A (\n, aka NEWLINE)
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xC0\x8A\"}", "illegal UTF-8 sequence");
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xE0\x80\x8A\"}", "illegal UTF-8 sequence");
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xF0\x80\x80\x8A\"}", "illegal UTF-8 sequence");
+
+  // Two invalid encodings for U+00A9 (COPYRIGHT SYMBOL)
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xE0\x81\xA9\"}", "illegal UTF-8 sequence");
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xF0\x80\x81\xA9\"}", "illegal UTF-8 sequence");
+
+  // Invalid encoding for U+20AC (EURO SYMBOL)
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    "{ F:\"\xF0\x82\x82\xAC\"}", "illegal UTF-8 sequence");
+
+  // UTF-16 surrogate values between U+D800 and U+DFFF cannot be encoded in UTF-8
+  TestError(
+    "table T { F:string; }"
+    "root_type T;"
+    // U+10400 "encoded" as U+D801 U+DC00
+    "{ F:\"\xED\xA0\x81\xED\xB0\x80\"}", "illegal UTF-8 sequence");
+}
+
 void UnknownFieldsTest() {
   flatbuffers::IDLOptions opts;
   opts.skip_unexpected_fields_in_json = true;
@@ -968,7 +1225,8 @@
 
   std::string jsongen;
   parser.opts.indent_step = -1;
-  GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  auto result = GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen);
+  TEST_EQ(result, true);
   TEST_EQ(jsongen == "{str: \"test\",i: 10}", true);
 }
 
@@ -980,6 +1238,29 @@
                        "table V { X:U; }"
                        "root_type V;"
                        "{ X:{ A:1 }, X_type: T }"), true);
+  // Unions must be parsable with prefixed namespace.
+  flatbuffers::Parser parser2;
+  TEST_EQ(parser2.Parse("namespace N; table A {} namespace; union U { N.A }"
+                        "table B { e:U; } root_type B;"
+                        "{ e_type: N_A, e: {} }"), true);
+}
+
+void ConformTest() {
+  flatbuffers::Parser parser;
+  TEST_EQ(parser.Parse("table T { A:int; } enum E:byte { A }"), true);
+
+  auto test_conform = [&](const char *test, const char *expected_err) {
+    flatbuffers::Parser parser2;
+    TEST_EQ(parser2.Parse(test), true);
+    auto err = parser2.ConformTo(parser);
+    TEST_NOTNULL(strstr(err.c_str(), expected_err));
+  };
+
+  test_conform("table T { A:byte; }", "types differ for field");
+  test_conform("table T { B:int; A:int; }", "offsets differ for field");
+  test_conform("table T { A:int = 1; }", "defaults differ for field");
+  test_conform("table T { B:float; }", "field renamed to different type");
+  test_conform("enum E:byte { B, A }", "values differ for enum");
 }
 
 int main(int /*argc*/, const char * /*argv*/[]) {
@@ -993,6 +1274,10 @@
 
   MutateFlatBuffersTest(flatbuf.get(), rawbuf.length());
 
+  ObjectFlatBuffersTest(flatbuf.get());
+
+  SizePrefixedTest();
+
   #ifndef FLATBUFFERS_NO_FILE_TESTS
   ParseAndGenerateTextTest();
   ReflectionTest(flatbuf.get(), rawbuf.length());
@@ -1007,10 +1292,14 @@
   EnumStringsTest();
   IntegerOutOfRangeTest();
   UnicodeTest();
+  UnicodeTestAllowNonUTF8();
+  UnicodeTestGenerateTextFailsOnNonUTF8();
   UnicodeSurrogatesTest();
   UnicodeInvalidSurrogatesTest();
+  InvalidUTF8Test();
   UnknownFieldsTest();
   ParseUnionTest();
+  ConformTest();
 
   if (!testing_fails) {
     TEST_OUTPUT_LINE("ALL TESTS PASSED");