diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..84e64f6
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+.jiri
diff --git a/go/src/v.io/mojo/client/client.go b/go/src/v.io/mojo/client/client.go
new file mode 100644
index 0000000..e05fd7b
--- /dev/null
+++ b/go/src/v.io/mojo/client/client.go
@@ -0,0 +1,15 @@
+package v23
+
+import (
+	"mojo/public/go/application"
+	"mojo/public/go/bindings"
+
+	"mojo/public/interfaces/bindings/v23proxy"
+)
+
+func ConnectToRemoteService(ctx application.Context, r application.ServiceRequest, v23Name string) {
+	v23r, v23p := v23proxy.CreateMessagePipeForV23()
+	ctx.ConnectToApplication("mojo:v23proxy").ConnectToService(&v23r)
+	prox := v23proxy.NewV23Proxy(v23p, bindings.GetAsyncWaiter())
+	prox.SetupProxy(v23Name, r.Type(), r.Desc(), r.Name(), r.PassMessagePipe())
+}
diff --git a/go/src/v.io/mojo/proxy/fake_service.go b/go/src/v.io/mojo/proxy/fake_service.go
new file mode 100644
index 0000000..a289776
--- /dev/null
+++ b/go/src/v.io/mojo/proxy/fake_service.go
@@ -0,0 +1,306 @@
+package main
+
+import (
+	"fmt"
+	"log"
+	"strings"
+
+	"v.io/v23/context"
+	"v.io/v23/rpc"
+
+	"mojo/public/go/application"
+	"mojo/public/go/bindings"
+	"mojo/public/go/mojovdl"
+	"mojo/public/go/system"
+
+	"v.io/v23/vdl"
+	"v.io/v23/vdlroot/signature"
+
+	"mojo/public/interfaces/bindings/mojom_types"
+	"mojo/public/interfaces/bindings/service_describer"
+)
+
+// As long as fakeService meets the Invoker interface, it is allowed to pass as
+// a universal v23 service.
+// See the function objectToInvoker in v.io/x/ref/runtime/internal/rpc/server.go
+type fakeService struct {
+	appctx application.Context
+	suffix string
+	router *bindings.Router
+	ids    bindings.Counter
+}
+
+// Prepare is used by the Fake Service to prepare the placeholders for the
+// input data.
+func (fs fakeService) Prepare(ctx *context.T, method string, numArgs int) (argptrs []interface{}, tags []*vdl.Value, _ error) {
+	inargs := make([]*vdl.Value, numArgs)
+	inptrs := make([]interface{}, len(inargs))
+	for i := range inargs {
+		inptrs[i] = &inargs[i]
+	}
+	return inptrs, nil, nil
+}
+
+// Wraps the interface request and the name of the requested mojo service.
+type v23ServiceRequest struct {
+	request bindings.InterfaceRequest
+	name    string
+}
+
+func (v *v23ServiceRequest) Name() string {
+	return v.name
+}
+
+func (v *v23ServiceRequest) Type() mojom_types.MojomInterface {
+	panic("not supported")
+}
+
+func (v *v23ServiceRequest) Desc() map[string]mojom_types.UserDefinedType {
+	panic("not supported")
+}
+
+func (v *v23ServiceRequest) PassMessagePipe() system.MessagePipeHandle {
+	return v.request.PassMessagePipe()
+}
+
+// Invoke calls the mojom service based on the suffix and converts the mojom
+// results (a struct) to Vanadium results (a slice of *vdl.Value).
+// Note: The argptrs from Prepare are reused here. The vom bytes should have
+// been decoded into these argptrs, so there are actual values inside now.
+func (fs fakeService) Invoke(ctx *context.T, call rpc.StreamServerCall, method string, argptrs []interface{}) (results []interface{}, _ error) {
+	// fs.suffix consists of the mojo url and the application/interface name.
+	// The last part should be the name; everything else is the url.
+	parts := strings.Split(fs.suffix, "/")
+	mojourl := strings.Join(parts[:len(parts)-1], "/") // e.g., mojo:go_remote_echo_server. May be defined in a BUILD.gn file.
+	mojoname := parts[len(parts)-1]                    // e.g., mojo::examples::RemoteEcho. Defined from the interface + module.
+
+	// Create the generic message pipe. r is a bindings.InterfaceRequest, and
+	// p is a bindings.InterfacePointer.
+	r, p := bindings.CreateMessagePipeForMojoInterface()
+	v := v23ServiceRequest{
+		request: r,
+		name:    mojoname,
+	} // v is an application.ServiceRequest with mojoname
+
+	// Connect to the mojourl.
+	fs.appctx.ConnectToApplication(mojourl).ConnectToService(&v)
+
+	// Then assign a new router the FakeService.
+	// This will never conflict because each FakeService is only invoked once.
+	fs.router = bindings.NewRouter(p.PassMessagePipe(), bindings.GetAsyncWaiter())
+	defer fs.Close_Proxy()
+
+	log.Printf("Fake Service Invoke (Remote Signature)")
+
+	// Vanadium relies on type information, so we will retrieve that first.
+	mojomInterface, desc, err := fs.callRemoteSignature(mojourl, mojoname)
+	if err != nil {
+		return nil, err
+	}
+
+	log.Printf("Fake Service Invoke Signature %v", mojomInterface)
+	log.Printf("Fake Service Invoke (Remote Method)")
+
+	// With the type information, we can make the method call to the remote interface.
+	methodResults, err := fs.callRemoteMethod(method, mojomInterface, desc, argptrs)
+	if err != nil {
+		return nil, err
+	}
+
+	log.Printf("Fake Service Invoke Results %v", methodResults)
+
+	// Convert methodResult to results.
+	results = make([]interface{}, len(methodResults))
+	for i := range methodResults {
+		results[i] = &methodResults[i]
+	}
+	return results, nil
+}
+
+func (fs fakeService) Close_Proxy() {
+	fs.router.Close()
+}
+
+// callRemoteSignature obtains type and header information from the remote
+// mojo service. Remote mojo interfaces all define a signature method.
+func (fs fakeService) callRemoteSignature(mojourl string, mojoname string) (mojomInterface mojom_types.MojomInterface, desc map[string]mojom_types.UserDefinedType, err error) {
+	/*log.Printf("callRemoteSignature: Prepare payload and header")
+
+	// Prepare the input for the mojo call.
+	// This consists of a payload and a header for the RemoteSignature.
+	payload := mojom_types.SignatureInput{}
+	header := bindings.MessageHeader{
+		Type:      0xffffffff,                          // Signature is always type 0xffffffff
+		Flags:     bindings.MessageExpectsResponseFlag, // It always has a response.
+		RequestId: fs.ids.Count(),
+	}
+
+	log.Printf("callRemoteSignature: Encode payload and header")
+
+	var message *bindings.Message
+	if message, err = bindings.EncodeMessage(header, &payload); err != nil {
+		return response, fmt.Errorf("can't encode request: %v", err.Error())
+	}
+
+	log.Printf("callRemoteSignature => callRemoteGeneric")
+
+	outMessage, err := fs.callRemoteGeneric(message)
+	if err != nil {
+		return response, err
+	}
+
+	log.Printf("callRemoteSignature: Decode response")
+
+	if err = outMessage.DecodePayload(&response); err != nil {
+		return
+	}
+
+	return response, nil*/
+
+	// TODO(afandria): The service_describer mojom file defines the constant, but
+	// it is not actually present in the generated code:
+	// https://github.com/domokit/mojo/issues/469
+	// serviceDescriberInterfaceName := "_ServiceDescriber"
+
+	r, p := service_describer.CreateMessagePipeForServiceDescriber()
+	fs.appctx.ConnectToApplication(mojourl).ConnectToService(&r)
+	sDescriber := service_describer.NewServiceDescriberProxy(p, bindings.GetAsyncWaiter())
+	defer sDescriber.Close_Proxy()
+
+	r2, p2 := service_describer.CreateMessagePipeForServiceDescription()
+	err = sDescriber.DescribeService(mojoname, r2)
+	if err != nil {
+		return
+	}
+	sDescription := service_describer.NewServiceDescriptionProxy(p2, bindings.GetAsyncWaiter())
+	defer sDescription.Close_Proxy()
+
+	mojomInterface, err = sDescription.GetTopLevelInterface()
+	if err != nil {
+		return
+	}
+	descPtr, err := sDescription.GetAllTypeDefinitions()
+	if err != nil {
+		return
+	}
+	return mojomInterface, *descPtr, nil
+}
+
+// A helper function that sends a remote message that expects a response.
+func (fs fakeService) callRemoteGeneric(message *bindings.Message) (outMessage *bindings.Message, err error) {
+	log.Printf("callRemoteGeneric: Send message along the router")
+
+	readResult := <-fs.router.AcceptWithResponse(message)
+	if err = readResult.Error; err != nil {
+		return
+	}
+
+	log.Printf("callRemoteGeneric: Audit response message header flag")
+	// The message flag we receive back must be a bindings.MessageIsResponseFlag
+	if readResult.Message.Header.Flags != bindings.MessageIsResponseFlag {
+		err = &bindings.ValidationError{bindings.MessageHeaderInvalidFlags,
+			fmt.Sprintf("invalid message header flag: %v", readResult.Message.Header.Flags),
+		}
+		return
+	}
+
+	log.Printf("callRemoteGeneric: Audit response message header type")
+	// While the mojo service we called into will return a header whose
+	// type must match our outgoing one.
+	if got, want := readResult.Message.Header.Type, message.Header.Type; got != want {
+		err = &bindings.ValidationError{bindings.MessageHeaderUnknownMethod,
+			fmt.Sprintf("invalid method in response: expected %v, got %v", want, got),
+		}
+		return
+	}
+
+	return readResult.Message, nil
+}
+
+// callRemoteMethod calls the method remotely in a generic way.
+// Produces []*vdl.Value at the end for the invoker to return.
+func (fs fakeService) callRemoteMethod(method string, mi mojom_types.MojomInterface, desc map[string]mojom_types.UserDefinedType, argptrs []interface{}) ([]*vdl.Value, error) {
+	// We need to parse the signature result to get the method relevant info out.
+	found := false
+	var ordinal uint32
+	for ord, mm := range mi.Methods {
+		if *mm.DeclData.ShortName == method {
+			ordinal = ord
+			found = true
+			break
+		}
+	}
+
+	if !found {
+		return nil, fmt.Errorf("callRemoteMethod: method %s does not exist", method)
+	}
+
+	mm := mi.Methods[ordinal]
+
+	// A void function must have request id of 0, whereas one with response params
+	// should  have a unique request id.
+	var rqId uint64
+	var flag uint32
+	if mm.ResponseParams != nil {
+		rqId = fs.ids.Count()
+		flag = bindings.MessageExpectsResponseFlag
+	} else {
+		flag = bindings.MessageNoFlag
+	}
+
+	header := bindings.MessageHeader{
+		Type:      ordinal,
+		Flags:     flag,
+		RequestId: rqId,
+	}
+
+	// Now produce the *bindings.Message that we will send to the other side.
+	inType := mojovdl.MojomStructToVDLType(mm.Parameters, desc)
+	message, err := encodeMessageFromVom(header, argptrs, inType)
+	if err != nil {
+		return nil, err
+	}
+
+	// Handle the 0 out-arg case first.
+	if mm.ResponseParams == nil {
+		if err = fs.router.Accept(message); err != nil {
+			return nil, err
+		}
+		return make([]*vdl.Value, 0), nil
+	}
+
+	// Otherwise, make a generic call with the message.
+	outMessage, err := fs.callRemoteGeneric(message)
+	if err != nil {
+		return nil, err
+	}
+
+	// Decode the *vdl.Value from the mojom bytes and mojom type.
+	outType := mojovdl.MojomStructToVDLType(*mm.ResponseParams, desc)
+	outVdlValue, err := mojovdl.DecodeValue(outMessage.Payload, outType)
+	if err != nil {
+		return nil, fmt.Errorf("mojovdl.DecodeValue failed: %v", err)
+	}
+
+	// Then split the *vdl.Value (struct) into []*vdl.Value
+	response := splitVdlValueByMojomType(outVdlValue, outType)
+	return response, nil
+}
+
+// The fake service has no signature.
+func (fs fakeService) Signature(ctx *context.T, call rpc.ServerCall) ([]signature.Interface, error) {
+	log.Printf("Fake Service Signature???")
+	return nil, nil
+}
+
+// The fake service knows nothing about method signatures.
+func (fs fakeService) MethodSignature(ctx *context.T, call rpc.ServerCall, method string) (signature.Method, error) {
+	log.Printf("Fake Service Method Signature???")
+	return signature.Method{}, nil
+}
+
+// The fake service will never need to glob.
+func (fs fakeService) Globber() *rpc.GlobState {
+	log.Printf("Fake Service Globber???")
+	return nil
+}
diff --git a/go/src/v.io/mojo/proxy/misc.go b/go/src/v.io/mojo/proxy/misc.go
new file mode 100644
index 0000000..d156b7f
--- /dev/null
+++ b/go/src/v.io/mojo/proxy/misc.go
@@ -0,0 +1,66 @@
+package main
+
+// Construct the proper *vdl.Value (as a struct) from the mojom type.
+import (
+	"fmt"
+
+	"mojo/public/go/bindings"
+	"mojo/public/go/mojovdl"
+
+	"v.io/v23/vdl"
+)
+
+// TODO(alexfandrianto): Since this function could panic, we should consider
+// handling that if it happens.
+func combineVdlValueByMojomType(values []*vdl.Value, t *vdl.Type) *vdl.Value {
+	outVdlValue := vdl.ZeroValue(t)
+	for i := 0; i < t.NumField(); i++ {
+		outVdlValue.StructField(i).Assign(values[i])
+	}
+	return outVdlValue
+}
+
+// Construct []*vdl.Value from a *vdl.Value (as a struct) via its mojom type.
+// TODO(alexfandrianto): Since this function could panic, we should consider
+// handling that if it happens.
+func splitVdlValueByMojomType(value *vdl.Value, t *vdl.Type) []*vdl.Value {
+	outVdlValues := make([]*vdl.Value, t.NumField())
+	for i := 0; i < t.NumField(); i++ {
+		outVdlValues[i] = value.StructField(i)
+	}
+	return outVdlValues
+}
+
+func encodeMessageFromVom(header bindings.MessageHeader, argptrs []interface{}, t *vdl.Type) (*bindings.Message, error) {
+	// Convert argptrs into their true form: []*vdl.Value
+	inargs := make([]*vdl.Value, len(argptrs))
+	for i := range argptrs {
+		inargs[i] = *argptrs[i].(**vdl.Value)
+	}
+
+	// Construct the proper *vdl.Value (as a struct) from the mojom type.
+	vdlValue := combineVdlValueByMojomType(inargs, t)
+
+	encoder := bindings.NewEncoder()
+	if err := header.Encode(encoder); err != nil {
+		return nil, err
+	}
+	if bytes, handles, err := encoder.Data(); err != nil {
+		return nil, err
+	} else {
+		// Encode here.
+		moreBytes, err := mojovdl.Encode(vdlValue)
+		if err != nil {
+			return nil, fmt.Errorf("mojovdl.Encode failed: %v", err)
+		}
+		// Append the encoded "payload" to the end of the slice.
+		bytes = append(bytes, moreBytes...)
+
+		return &bindings.Message{
+			Header:  header,
+			Bytes:   bytes,
+			Handles: handles,
+			Payload: moreBytes,
+		}, nil
+	}
+}
diff --git a/go/src/v.io/mojo/proxy/proxy.go b/go/src/v.io/mojo/proxy/proxy.go
new file mode 100644
index 0000000..26a9f64
--- /dev/null
+++ b/go/src/v.io/mojo/proxy/proxy.go
@@ -0,0 +1,269 @@
+package main
+
+import (
+	"flag"
+	"fmt"
+	"log"
+
+	"v.io/v23"
+	"v.io/v23/context"
+	"v.io/v23/options"
+	"v.io/v23/security"
+	"v.io/v23/vdl"
+
+	"mojo/public/go/application"
+	"mojo/public/go/bindings"
+	"mojo/public/go/mojovdl"
+	"mojo/public/go/system"
+	"mojo/public/interfaces/bindings/mojom_types"
+	"mojo/public/interfaces/bindings/v23proxy"
+
+	_ "v.io/x/ref/runtime/factories/static"
+)
+
+//#include "mojo/public/c/system/types.h"
+import "C"
+
+func init() {
+	flag.String("child-connection-id", "", "")
+	flag.String("mojo-platform-channel-handle", "", "")
+}
+
+type v23HeaderReceiver struct {
+	delegate    *V23ServerDelegate
+	v23Name     string
+	ifaceSig    mojom_types.MojomInterface
+	desc        map[string]mojom_types.UserDefinedType
+	serviceName string
+	handle      system.MessagePipeHandle
+}
+
+func (r *v23HeaderReceiver) SetupProxy(v23Name string, ifaceSig mojom_types.MojomInterface, desc map[string]mojom_types.UserDefinedType, serviceName string, handle system.MessagePipeHandle) (err error) {
+	log.Printf("[server] In SetupProxy(%s, %v, %v, %s, %v)\n", v23Name, ifaceSig, desc, serviceName, handle)
+	r.v23Name = v23Name
+	r.ifaceSig = ifaceSig
+	r.desc = desc
+	r.serviceName = serviceName
+	r.handle = handle
+
+	go func() {
+		connector := bindings.NewConnector(r.handle, bindings.GetAsyncWaiter())
+
+		// Read generic calls in a loop
+		stub := &genericStub{
+			header:    r,
+			ctx:       r.delegate.ctx,
+			connector: connector,
+		}
+		bindingStub := bindings.NewStub(connector, stub)
+		for {
+			if err := bindingStub.ServeRequest(); err != nil {
+				connectionError, ok := err.(*bindings.ConnectionError)
+				if !ok || !connectionError.Closed() {
+					log.Println(err)
+				}
+				break
+			}
+		}
+		r.delegate.stubs = append(r.delegate.stubs, bindingStub)
+	}()
+	return nil
+}
+
+type byteCopyingPayload []byte
+
+func (bcp byteCopyingPayload) Encode(encoder *bindings.Encoder) error {
+	encoder.WriteRawBytes(bcp)
+	return nil
+}
+
+func (bcp byteCopyingPayload) Decode(decoder *bindings.Decoder) error {
+	panic("not supported")
+}
+
+type genericStub struct {
+	header    *v23HeaderReceiver
+	ctx       *context.T
+	connector *bindings.Connector
+}
+
+func (s *genericStub) Accept(message *bindings.Message) (err error) {
+	/*if int(message.Header.Type) >= len(s.header.ifaceSig.Methods) {
+		return fmt.Errorf("Method had index %d, but interface only has %d methods",
+			message.Header.Type, len(s.header.ifaceSig.Methods))
+	}*/
+	if _, ok := s.header.ifaceSig.Methods[message.Header.Type]; !ok {
+		return fmt.Errorf("Method had index %d, but interface only has %d methods",
+			message.Header.Type, len(s.header.ifaceSig.Methods))
+	}
+
+	methodSig := s.header.ifaceSig.Methods[message.Header.Type]
+	methodName := *methodSig.DeclData.ShortName
+	// Should we perform validation of flags like generated methods?
+	// Does this handle 0-arg methods?
+
+	messageBytes := message.Payload
+
+	response, err := s.Call(s.header.v23Name, methodName, messageBytes, methodSig.Parameters, methodSig.ResponseParams)
+	if err != nil {
+		return err
+	}
+	responseHeader := bindings.MessageHeader{
+		Type:      message.Header.Type,
+		Flags:     bindings.MessageIsResponseFlag,
+		RequestId: message.Header.RequestId,
+	}
+	responseMessage, err := bindings.EncodeMessage(responseHeader, byteCopyingPayload(response))
+	if err != nil {
+		return err
+	}
+	return s.connector.WriteMessage(responseMessage)
+}
+
+func (s *genericStub) Call(name, method string, value []byte, inParamsType mojom_types.MojomStruct, outParamsType *mojom_types.MojomStruct) ([]byte, error) {
+	log.Printf("server: %s.%s: %#v", name, method, inParamsType)
+
+	inVType := mojovdl.MojomStructToVDLType(inParamsType, s.header.desc)
+	var outVType *vdl.Type
+	if outParamsType != nil {
+		outVType = mojovdl.MojomStructToVDLType(*outParamsType, s.header.desc)
+	}
+
+	// Decode the vdl.Value from the mojom bytes and mojom type.
+	inVdlValue, err := mojovdl.DecodeValue(value, inVType)
+	if err != nil {
+		return nil, fmt.Errorf("mojovdl.DecodeValue failed: %v", err)
+	}
+
+	// inVdlValue is a struct, but we need to send []interface.
+	inargs := splitVdlValueByMojomType(inVdlValue, inVType)
+	inargsIfc := make([]interface{}, len(inargs))
+	for i := range inargs {
+		inargsIfc[i] = inargs[i]
+	}
+
+	// We know that the v23proxy (on the other side) will give us back a bunch of
+	// data in []interface{}. so we'll want to decode them into *vdl.Value.
+	log.Printf("%s %v\n", method, outParamsType)
+	outargs := make([]*vdl.Value, len(outParamsType.Fields))
+	outptrs := make([]interface{}, len(outargs))
+	for i := range outargs {
+		outptrs[i] = &outargs[i]
+	}
+
+	// Now, run the call without any authorization.
+	if err := v23.GetClient(s.ctx).Call(s.ctx, name, method, inargsIfc, outptrs, options.SkipServerEndpointAuthorization{}); err != nil {
+		return nil, err
+	}
+
+	// Now convert the []interface{} into a *vdl.Value (struct).
+	outVdlValue := combineVdlValueByMojomType(outargs, outVType)
+
+	// Finally, encode this *vdl.Value (struct) into mojom bytes and send the response.
+	result, err := mojovdl.Encode(outVdlValue)
+	if err != nil {
+		return nil, fmt.Errorf("mojovdl.Encode failed: %v", err)
+	}
+	return result, nil
+}
+
+type V23ServerDelegate struct {
+	ctx      *context.T
+	stubs    []*bindings.Stub
+	shutdown v23.Shutdown
+}
+
+func (delegate *V23ServerDelegate) Initialize(context application.Context) {
+	log.Printf("V23ServerDelegate.Initialize...")
+
+	// Start up v23 whenever a v23proxy is begun.
+	// This is done regardless of whether we are initializing this v23proxy for use
+	// as a client or as a server.
+	ctx, shutdown := v23.Init()
+	delegate.ctx = ctx
+	delegate.shutdown = shutdown
+
+	// TODO(alexfandrianto): Does Mojo stop us from creating too many v23proxy?
+	// Is it 1 per shell? Ideally, each device will only serve 1 of these v23proxy,
+	// but it is not problematic to have extra.
+	/*s := MakeServer(ctx)
+	err := s.ServeDispatcher("", &V23ProxyDispatcher{
+		appctx: context,
+	})*/
+	_, s, err := v23.WithNewDispatchingServer(ctx, "", &V23ProxyDispatcher{
+		appctx: context,
+	})
+	if err != nil {
+		log.Panic("Error serving service: ", err)
+	}
+
+	endpoints := s.Status().Endpoints
+	fmt.Printf("Listening at: /%v\n", endpoints[0])
+}
+
+/*func MakeServer(ctx *context.T) rpc.Server {
+	s, err := v23.NewServer(ctx)
+	if err != nil {
+		log.Panic("Failure creating server: ", err)
+	}
+
+	endpoints, err := s.Listen(v23.GetListenSpec(ctx))
+	if err != nil {
+		log.Panic("Error listening to service: ", err)
+	}
+	fmt.Printf("Listening at: /%v\n", endpoints[0])
+	return s
+}*/
+
+type V23ProxyDispatcher struct {
+	appctx application.Context
+}
+
+func (v23pd *V23ProxyDispatcher) Lookup(ctx *context.T, suffix string) (interface{}, security.Authorizer, error) {
+	log.Printf("Dispatcher: %s", suffix)
+	return fakeService{
+		appctx: v23pd.appctx,
+		suffix: suffix,
+		ids:    bindings.NewCounter(),
+	}, security.AllowEveryone(), nil
+}
+
+func (delegate *V23ServerDelegate) Create(request v23proxy.V23_Request) {
+	headerReceiver := &v23HeaderReceiver{delegate: delegate}
+	v23Stub := v23proxy.NewV23Stub(request, headerReceiver, bindings.GetAsyncWaiter())
+	delegate.stubs = append(delegate.stubs, v23Stub)
+
+	go func() {
+		// Read header message
+		if err := v23Stub.ServeRequest(); err != nil {
+			connectionError, ok := err.(*bindings.ConnectionError)
+			if !ok || !connectionError.Closed() {
+				log.Println(err)
+			}
+			return
+		}
+	}()
+}
+
+func (delegate *V23ServerDelegate) AcceptConnection(connection *application.Connection) {
+	log.Printf("V23ServerDelegate.AcceptConnection...")
+	connection.ProvideServices(&v23proxy.V23_ServiceFactory{delegate})
+}
+
+func (delegate *V23ServerDelegate) Quit() {
+	log.Printf("V23ServerDelegate.Quit...")
+	for _, stub := range delegate.stubs {
+		stub.Close()
+	}
+
+	delegate.shutdown()
+}
+
+//export MojoMain
+func MojoMain(handle C.MojoHandle) C.MojoResult {
+	application.Run(&V23ServerDelegate{}, system.MojoHandle(handle))
+	return C.MOJO_RESULT_OK
+}
+
+func main() {
+}
diff --git a/go/src/v.io/mojo/transcoder/allocation_size.go b/go/src/v.io/mojo/transcoder/allocation_size.go
new file mode 100644
index 0000000..ff70e88
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/allocation_size.go
@@ -0,0 +1,37 @@
+package mojovdl
+
+import "v.io/v23/vdl"
+
+func neededStructAllocationSize(vt *vdl.Type) uint32 {
+	var totalBits uint32
+	for fi := 0; fi < vt.NumField(); fi++ {
+		field := vt.Field(fi)
+		totalBits += baseTypeSizeBits(field.Type)
+	}
+	return roundBitsTo64Alignment(totalBits)
+}
+
+func baseTypeSizeBits(vt *vdl.Type) uint32 {
+	switch vt.Kind() {
+	case vdl.Bool:
+		return 1
+	case vdl.Byte:
+		return 8
+	case vdl.Uint16, vdl.Int16:
+		return 16
+	case vdl.Uint32, vdl.Int32, vdl.Float32, vdl.Enum:
+		return 32
+	case vdl.Union:
+		return 128 // Header + value / pointer to inner union
+	default: // Either Uint64, Int64, Float64 or pointer.
+		return 64
+	}
+}
+
+// Round up to the nearest 8 byte length.
+func roundBitsTo64Alignment(numBits uint32) uint32 {
+	if numBits%64 == 0 {
+		return numBits / 8
+	}
+	return (numBits + (64 - numBits%64)) / 8
+}
diff --git a/go/src/v.io/mojo/transcoder/allocator.go b/go/src/v.io/mojo/transcoder/allocator.go
new file mode 100644
index 0000000..0f3be60
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/allocator.go
@@ -0,0 +1,75 @@
+package mojovdl
+
+import "encoding/binary"
+
+const HEADER_SIZE uint32 = 8
+
+// TODO(bprosnitz) maybe make an interface to support decode too
+type allocator struct {
+	// Buffer containing encoded data.
+	buf []byte
+
+	// Index of the first unclaimed byte in buf.
+	end uint32
+}
+
+func (a *allocator) makeRoom(size uint32) {
+	totalNeeded := a.end + size
+
+	allocationSize := uint32(1)
+	for allocationSize < totalNeeded {
+		allocationSize *= 2
+	}
+
+	if allocationSize != uint32(len(a.buf)) {
+		oldBuf := a.buf
+		a.buf = make([]byte, allocationSize)
+		copy(a.buf, oldBuf)
+	}
+}
+
+func (a *allocator) allocateBlock(size uint32, numElems uint32) (startIndex, endIndex uint32) {
+	size_with_header := size + HEADER_SIZE
+	size_with_header_rounded := size_with_header
+	if size_with_header%8 != 0 {
+		size_with_header_rounded = size_with_header + (8 - (size_with_header % 8))
+	}
+
+	a.makeRoom(size_with_header_rounded)
+	binary.LittleEndian.PutUint32(a.buf[a.end:a.end+4], size_with_header)
+	binary.LittleEndian.PutUint32(a.buf[a.end+4:a.end+8], numElems)
+
+	prevEnd := a.end
+	start := prevEnd + HEADER_SIZE
+	end := prevEnd + size_with_header
+	a.end = prevEnd + size_with_header_rounded
+	return start, end
+}
+
+func (a *allocator) Allocate(size uint32, numElems uint32) bytesRef {
+	begin, end := a.allocateBlock(size, numElems)
+	ref := bytesRef{
+		allocator:  a,
+		startIndex: begin,
+		endIndex:   end,
+		// zeros
+	}
+	return ref
+}
+
+func (a *allocator) AllocationFromPointer(absoluteIndex uint32) bytesRef {
+	headerPos := absoluteIndex - HEADER_SIZE
+	size := binary.LittleEndian.Uint32(a.buf[headerPos : headerPos+4])
+	return bytesRef{
+		allocator:  a,
+		startIndex: absoluteIndex,
+		endIndex:   absoluteIndex + size,
+	}
+}
+
+func (a *allocator) AllocatedBytes() []byte {
+	if a.buf == nil {
+		return []byte{}
+	}
+	return a.buf[:a.end]
+}
diff --git a/go/src/v.io/mojo/transcoder/decode.go b/go/src/v.io/mojo/transcoder/decode.go
new file mode 100644
index 0000000..b5b7142
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/decode.go
@@ -0,0 +1,370 @@
+package mojovdl
+
+import (
+	"fmt"
+	"reflect"
+
+	"mojo/public/go/bindings"
+
+	"v.io/v23/vdl"
+)
+
+// Decode decodes the mojom-encoded data into valptr, which must be a pointer to
+// the desired value.  The datatype describes the type of the encoded data.
+// Returns an error if the data cannot be decoded into valptr, based on the VDL
+// value conversion rules.
+func Decode(data []byte, datatype *vdl.Type, valptr interface{}) error {
+	target, err := vdl.ReflectTarget(reflect.ValueOf(valptr))
+	if err != nil {
+		return err
+	}
+	d := &decoder{dec: bindings.NewDecoder(data, nil)}
+	return d.decodeValue(datatype, target, true, false)
+}
+
+// DecodeValue is like Decode, but decodes mojom-encoded data into a vdl.Value.
+func DecodeValue(data []byte, datatype *vdl.Type) (*vdl.Value, error) {
+	v := new(vdl.Value)
+	if err := Decode(data, datatype, &v); err != nil {
+		return nil, err
+	}
+	return v, nil
+}
+
+type decoder struct {
+	dec       *bindings.Decoder
+	typeStack []*vdl.Type
+}
+
+func (d *decoder) decodeValue(vt *vdl.Type, target vdl.Target, isTopType, isNullable bool) error {
+	switch vt.Kind() {
+	case vdl.Bool:
+		value, err := d.dec.ReadBool()
+		if err != nil {
+			return err
+		}
+		return target.FromBool(value, vt)
+	case vdl.Int16:
+		value, err := d.dec.ReadInt16()
+		if err != nil {
+			return err
+		}
+		return target.FromInt(int64(value), vt)
+	case vdl.Int32:
+		value, err := d.dec.ReadInt32()
+		if err != nil {
+			return err
+		}
+		return target.FromInt(int64(value), vt)
+	case vdl.Int64:
+		value, err := d.dec.ReadInt64()
+		if err != nil {
+			return err
+		}
+		return target.FromInt(value, vt)
+	case vdl.Byte:
+		value, err := d.dec.ReadUint8()
+		if err != nil {
+			return err
+		}
+		return target.FromUint(uint64(value), vt)
+	case vdl.Uint16:
+		value, err := d.dec.ReadUint16()
+		if err != nil {
+			return err
+		}
+		return target.FromUint(uint64(value), vt)
+	case vdl.Uint32:
+		value, err := d.dec.ReadUint32()
+		if err != nil {
+			return err
+		}
+		return target.FromUint(uint64(value), vt)
+	case vdl.Uint64:
+		value, err := d.dec.ReadUint64()
+		if err != nil {
+			return err
+		}
+		return target.FromUint(value, vt)
+	case vdl.Float32:
+		value, err := d.dec.ReadFloat32()
+		if err != nil {
+			return err
+		}
+		return target.FromFloat(float64(value), vt)
+	case vdl.Float64:
+		value, err := d.dec.ReadFloat64()
+		if err != nil {
+			return err
+		}
+		return target.FromFloat(value, vt)
+	case vdl.String:
+		switch ptr, err := d.dec.ReadPointer(); {
+		case err != nil:
+			return err
+		case ptr == 0:
+			return fmt.Errorf("invalid null string pointer")
+		default:
+			value, err := d.dec.ReadString()
+			if err != nil {
+				return err
+			}
+			return target.FromString(value, vt)
+		}
+		return nil
+	case vdl.Enum:
+		index, err := d.dec.ReadInt32()
+		if err != nil {
+			return err
+		}
+		if int(index) >= vt.NumEnumLabel() || index < 0 {
+			return fmt.Errorf("enum label out of range")
+		}
+		target.FromEnumLabel(vt.EnumLabel(int(index)), vt)
+		return nil
+	case vdl.Complex64:
+		panic("unimplemented")
+	case vdl.Complex128:
+		panic("unimplemented")
+	case vdl.Array, vdl.List:
+		switch ptr, err := d.dec.ReadPointer(); {
+		case err != nil:
+			return err
+		case ptr == 0 && isNullable:
+			return target.FromNil(vdl.OptionalType(vt))
+		case ptr == 0 && !isNullable:
+			return fmt.Errorf("invalid null struct pointer")
+		}
+
+		if vt.IsBytes() {
+			str, err := d.dec.ReadString()
+			if err != nil {
+				return err
+			}
+			return target.FromBytes([]byte(str), vt)
+		} else {
+			elemBitSize := baseTypeSizeBits(vt.Elem())
+			numElems, err := d.dec.StartArray(elemBitSize)
+			if err != nil {
+				return err
+			}
+			listTarget, err := target.StartList(vt, int(numElems))
+			if err != nil {
+				return err
+			}
+			for i := 0; i < int(numElems); i++ {
+				elemTarget, err := listTarget.StartElem(i)
+				if err != nil {
+					return err
+				}
+				if err := d.decodeValue(vt.Elem(), elemTarget, false, false); err != nil {
+					return err
+				}
+				if err := listTarget.FinishElem(elemTarget); err != nil {
+					return err
+				}
+			}
+			if err := target.FinishList(listTarget); err != nil {
+				return err
+			}
+		}
+		return d.dec.Finish()
+	case vdl.Set:
+		panic("unimplemented")
+		/*switch ptr, err := d.dec.ReadPointer(); {
+		case err != nil:
+			return err
+		case ptr == 0 && isNullable:
+			return target.FromNil(vdl.OptionalType(vt))
+		case ptr == 0 && !isNullable:
+			return fmt.Errorf("invalid null struct pointer")
+		}
+		keyBitSize := baseTypeSizeBits(vt.Key())
+		numKeys, err := d.dec.StartArray(keyBitSize)
+		if err != nil {
+			return err
+		}
+		setTarget, err := target.StartSet(vt, int(numKeys))
+		if err != nil {
+			return err
+		}
+		for i := 0; i < int(numKeys); i++ {
+			keyTarget, err := setTarget.StartKey()
+			if err != nil {
+				return err
+			}
+			if err := d.decodeValue(mt.Key, keyTarget, false, false); err != nil {
+				return err
+			}
+			if err := setTarget.FinishKey(keyTarget); err != nil {
+				return err
+			}
+		}
+		if err := target.FinishSet(setTarget); err != nil {
+			return err
+		}
+		return d.dec.Finish()*/
+	case vdl.Map:
+		switch ptr, err := d.dec.ReadPointer(); {
+		case err != nil:
+			return err
+		case ptr == 0 && isNullable:
+			return target.FromNil(vdl.OptionalType(vt))
+		case ptr == 0 && !isNullable:
+			return fmt.Errorf("invalid null struct pointer")
+		}
+		if err := d.dec.StartMap(); err != nil {
+			return err
+		}
+		var keys, values []*vdl.Value
+		keysTarget, err := vdl.ReflectTarget(reflect.ValueOf(&keys))
+		if err != nil {
+			return err
+		}
+		keysListType := vdl.ListType(vt.Key())
+		if err := d.decodeValue(keysListType, keysTarget, false, false); err != nil {
+			return err
+		}
+		valuesTarget, err := vdl.ReflectTarget(reflect.ValueOf(&values))
+		if err != nil {
+			return err
+		}
+		valuesListType := vdl.ListType(vt.Elem())
+		if err := d.decodeValue(valuesListType, valuesTarget, false, false); err != nil {
+			return err
+		}
+
+		if len(keys) != len(values) {
+			return fmt.Errorf("values don't match keys")
+		}
+		mapTarget, err := target.StartMap(vt, len(keys))
+		if err != nil {
+			return err
+		}
+		for i, key := range keys {
+			value := values[i]
+
+			keyTarget, err := mapTarget.StartKey()
+			if err != nil {
+				return err
+			}
+			if err := vdl.FromValue(keyTarget, key); err != nil {
+				return err
+			}
+			fieldTarget, err := mapTarget.FinishKeyStartField(keyTarget)
+			if err != nil {
+				return err
+			}
+			if err := vdl.FromValue(fieldTarget, value); err != nil {
+				return err
+			}
+			if err := mapTarget.FinishField(keyTarget, fieldTarget); err != nil {
+				return err
+			}
+		}
+		if err := target.FinishMap(mapTarget); err != nil {
+			return err
+		}
+
+		return d.dec.Finish()
+	case vdl.Struct:
+		// TODO(toddw): See the comment in encoder.mojomStructSize; we rely on the
+		// fields to be presented in the canonical mojom field ordering.
+		if !isTopType {
+			switch ptr, err := d.dec.ReadPointer(); {
+			case err != nil:
+				return err
+			case ptr == 0 && isNullable:
+				return target.FromNil(vdl.OptionalType(vt))
+			case ptr == 0 && !isNullable:
+				return fmt.Errorf("invalid null struct pointer")
+			}
+		}
+		_, err := d.dec.StartStruct()
+		if err != nil {
+			return err
+		}
+		targetFields, err := target.StartFields(vt)
+		if err != nil {
+			return err
+		}
+		for i := 0; i < vt.NumField(); i++ {
+			mfield := vt.Field(i)
+			switch vkey, vfield, err := targetFields.StartField(mfield.Name); {
+			// TODO(toddw): Handle err == vdl.ErrFieldNoExist case?
+			case err != nil:
+				return err
+			default:
+				if err := d.decodeValue(mfield.Type, vfield, false, false); err != nil {
+					return err
+				}
+				if err := targetFields.FinishField(vkey, vfield); err != nil {
+					return err
+				}
+			}
+		}
+		// TODO(toddw): Fill in fields that weren't decoded with their zero value.
+		if err := target.FinishFields(targetFields); err != nil {
+			return err
+		}
+		return d.dec.Finish()
+	case vdl.Union:
+		size, tag, err := d.dec.ReadUnionHeader()
+		if err != nil {
+			return err
+		}
+		if size == 0 {
+			d.dec.SkipUnionValue()
+			return target.FromNil(vdl.OptionalType(vt))
+		}
+		if int(tag) >= vt.NumField() {
+			return fmt.Errorf("union tag out of bounds")
+		}
+		fld := vt.Field(int(tag))
+		targetFields, err := target.StartFields(vt)
+		if err != nil {
+			return err
+		}
+		vKey, vField, err := targetFields.StartField(fld.Name)
+		if err != nil {
+			return err
+		}
+		if fld.Type.Kind() == vdl.Union {
+			switch ptr, err := d.dec.ReadPointer(); {
+			case err != nil:
+				return err
+			case ptr == 0 && isNullable:
+				return target.FromNil(vdl.OptionalType(fld.Type))
+			case ptr == 0 && !isNullable:
+				return fmt.Errorf("invalid null union pointer")
+			}
+			if err := d.dec.StartNestedUnion(); err != nil {
+				return err
+			}
+		}
+		if err := d.decodeValue(fld.Type, vField, false, false); err != nil {
+			return err
+		}
+		if fld.Type.Kind() == vdl.Union {
+			if err := d.dec.Finish(); err != nil {
+				return err
+			}
+		}
+		if err := targetFields.FinishField(vKey, vField); err != nil {
+			return err
+		}
+		if err := target.FinishFields(targetFields); err != nil {
+			return err
+		}
+		d.dec.FinishReadingUnionValue()
+		return nil
+	case vdl.Optional:
+		return d.decodeValue(vt.Elem(), target, false, true)
+	case vdl.Any:
+		panic("unimplemented")
+	//case vdl.TypeObject:
+	//	panic("unimplemented")
+	default:
+		panic(fmt.Errorf("decodeValue unhandled vdl type: %v", vt))
+	}
+}
diff --git a/go/src/v.io/mojo/transcoder/encode.go b/go/src/v.io/mojo/transcoder/encode.go
new file mode 100644
index 0000000..b778e0e
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/encode.go
@@ -0,0 +1,94 @@
+package mojovdl
+
+import (
+	"reflect"
+
+	"v.io/v23/vdl"
+)
+
+func Encode(value interface{}) ([]byte, error) {
+	enc := &encoder{
+		allocator: &allocator{},
+	}
+	err := vdl.FromReflect(enc, reflect.ValueOf(value))
+	return enc.Bytes(), err
+}
+
+type encoder struct {
+	allocator *allocator
+}
+
+func (e *encoder) Bytes() []byte {
+	return e.allocator.AllocatedBytes()
+}
+
+func (e *encoder) FromBool(src bool, tt *vdl.Type) error {
+	panic("cannot encode top level bool")
+}
+func (e *encoder) FromUint(src uint64, tt *vdl.Type) error {
+	panic("cannot encode top level uint")
+}
+func (e *encoder) FromInt(src int64, tt *vdl.Type) error {
+	panic("cannot encode top level int")
+}
+func (e *encoder) FromFloat(src float64, tt *vdl.Type) error {
+	panic("cannot encode top level float")
+}
+func (e *encoder) FromComplex(src complex128, tt *vdl.Type) error {
+	panic("cannot encode top level complex")
+}
+func (e *encoder) FromBytes(src []byte, tt *vdl.Type) error {
+	panic("cannot encode top level bytes")
+}
+func (e *encoder) FromString(src string, tt *vdl.Type) error {
+	panic("cannot encode top level string")
+}
+func (e *encoder) FromEnumLabel(src string, tt *vdl.Type) error {
+	panic("cannot encode top level enum")
+}
+func (e *encoder) FromTypeObject(src *vdl.Type) error {
+	panic("cannot encode top level type object")
+}
+func (e *encoder) FromNil(tt *vdl.Type) error {
+	panic("cannot encode top level nil")
+}
+
+func (e *encoder) StartList(tt *vdl.Type, len int) (vdl.ListTarget, error) {
+	panic("UNIMPLEMENTED")
+	return nil, nil
+}
+func (e *encoder) FinishList(x vdl.ListTarget) error {
+	return nil
+}
+func (e *encoder) StartSet(tt *vdl.Type, len int) (vdl.SetTarget, error) {
+	panic("UNIMPLEMENTED")
+}
+func (e *encoder) FinishSet(x vdl.SetTarget) error {
+	panic("UNIMPLEMENTED")
+
+}
+func (e *encoder) StartMap(tt *vdl.Type, len int) (vdl.MapTarget, error) {
+	panic("UNIMPLEMENTED")
+
+}
+func (e *encoder) FinishMap(x vdl.MapTarget) error {
+	panic("UNIMPLEMENTED")
+
+}
+func (e *encoder) StartFields(tt *vdl.Type) (vdl.FieldsTarget, error) {
+	if tt.Kind() == vdl.Union {
+		panic("not yet supported")
+	}
+	if tt.Kind() == vdl.Optional {
+		tt = tt.Elem()
+	}
+	block := e.allocator.Allocate(neededStructAllocationSize(tt), 0)
+	return fieldsTarget{
+			vdlType: tt,
+			block:   block,
+		},
+		nil
+}
+func (e *encoder) FinishFields(x vdl.FieldsTarget) error {
+	return nil
+}
diff --git a/go/src/v.io/mojo/transcoder/ref.go b/go/src/v.io/mojo/transcoder/ref.go
new file mode 100644
index 0000000..9d53c75
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/ref.go
@@ -0,0 +1,35 @@
+package mojovdl
+
+type bytesRef struct {
+	allocator            *allocator
+	startIndex, endIndex uint32
+}
+
+func (b bytesRef) Slice(low, high uint32) bytesRef {
+	return bytesRef{
+		allocator:  b.allocator,
+		startIndex: b.startIndex + low,
+		endIndex:   b.startIndex + high,
+	}
+}
+
+// SignedSlice allows going backwards in the slice (temporary hack to include header in slice for unions)
+func (b bytesRef) SignedSlice(low, high int) bytesRef {
+	return bytesRef{
+		allocator:  b.allocator,
+		startIndex: uint32(int(b.startIndex) + low),
+		endIndex:   uint32(int(b.startIndex) + high),
+	}
+}
+
+func (b bytesRef) Bytes() []byte {
+	return b.allocator.buf[b.startIndex:b.endIndex]
+}
+
+func (b bytesRef) AsPointer(fromRefPos bytesRef) uint32 {
+	offset := b.startIndex - fromRefPos.startIndex
+	if offset <= 0 {
+		panic("invalid non-positive offset for pointer")
+	}
+	return offset - HEADER_SIZE
+}
diff --git a/go/src/v.io/mojo/transcoder/struct_offset.go b/go/src/v.io/mojo/transcoder/struct_offset.go
new file mode 100644
index 0000000..317a45b
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/struct_offset.go
@@ -0,0 +1,204 @@
+package mojovdl
+
+import (
+	"fmt"
+
+	"v.io/v23/vdl"
+)
+
+func offsetInStruct(index int, structVdlType *vdl.Type) (byteOffset uint32, bitOffset uint8) {
+	if index >= structVdlType.NumField() {
+		panic(fmt.Sprintf("index %v out of bounds for type %v", index, structVdlType))
+	}
+
+	offsetComputation := &structOffsetComputation{}
+	for i := 0; i < index; i++ {
+		bits := baseTypeSizeBits(structVdlType.Field(i).Type)
+		switch bits {
+		case 1:
+			offsetComputation.next1()
+		case 8:
+			offsetComputation.next8()
+		case 16:
+			offsetComputation.next16()
+		case 32:
+			offsetComputation.next32()
+		case 64:
+			offsetComputation.next64()
+		case 128:
+			offsetComputation.next64()
+			offsetComputation.next64()
+		default:
+			panic("unknown bit size")
+		}
+	}
+
+	switch baseTypeSizeBits(structVdlType.Field(index).Type) {
+	case 1:
+		return offsetComputation.index1, offsetComputation.bitOffset1
+	case 8:
+		return offsetComputation.index8, 0
+	case 16:
+		return offsetComputation.index16, 0
+	case 32:
+		return offsetComputation.index32, 0
+	case 64, 128:
+		return offsetComputation.index64, 0
+
+	default:
+		panic("unknown bit size")
+	}
+}
+
+type structOffsetComputation struct {
+	index8, index16, index32, index64 uint32
+	index1                            uint32
+	bitOffset1                        uint8
+}
+
+func (sa *structOffsetComputation) next1() {
+	newBitOffset1 := (sa.bitOffset1 + 1) % 8
+	var nextIndex uint32
+	if sa.index1 != sa.index8 {
+		nextIndex = sa.index8
+	} else {
+		nextIndex = sa.index1 + 1
+	}
+	if sa.bitOffset1 == 0 {
+		// bit offset == 0 means fetch a new byte
+		if sa.index8 == sa.index1 {
+			sa.index8 = nextIndex
+		}
+		if sa.index16 == sa.index1 {
+			if nextIndex&0x1 == 0 {
+				sa.index16 = nextIndex
+			} else {
+				sa.index16 = nextIndex + 1
+			}
+		}
+		if sa.index32 == sa.index1 {
+			if nextIndex&0x3 == 0 {
+				sa.index32 = nextIndex
+			} else {
+				sa.index32 = nextIndex + (4 - (nextIndex & 0x3))
+			}
+		}
+		if sa.index64 == sa.index1 {
+			if nextIndex&0x7 == 0 {
+				sa.index64 = nextIndex
+			} else {
+				sa.index64 = nextIndex + (8 - (nextIndex & 0x7))
+			}
+		}
+	}
+
+	if sa.bitOffset1 == 7 {
+		sa.index1 = nextIndex
+	}
+	sa.bitOffset1 = newBitOffset1
+}
+func (sa *structOffsetComputation) next8() {
+	var newIndex8 uint32
+	if sa.index8 != sa.index16 {
+		newIndex8 = sa.index16
+	} else {
+		newIndex8 = sa.index8 + 1
+	}
+
+	if sa.index1 == sa.index8 && sa.bitOffset1 == 0 {
+		sa.index1 = newIndex8
+	}
+	if sa.index16 == sa.index8 {
+		if newIndex8&0x1 == 0 {
+			sa.index16 = newIndex8
+		} else {
+			sa.index16 = newIndex8 + 1
+		}
+	}
+	if sa.index32 == sa.index8 {
+		if newIndex8&0x3 == 0 {
+			sa.index32 = newIndex8
+		} else {
+			sa.index32 = newIndex8 + (4 - (newIndex8 & 0x3))
+		}
+	}
+	if sa.index64 == sa.index8 {
+		if newIndex8&0x7 == 0 {
+			sa.index64 = newIndex8
+		} else {
+			sa.index64 = newIndex8 + (8 - (newIndex8 & 0x7))
+		}
+	}
+	sa.index8 = newIndex8
+}
+func (sa *structOffsetComputation) next16() {
+	var newIndex16 uint32
+	if sa.index16 != sa.index32 {
+		newIndex16 = sa.index32
+	} else {
+		newIndex16 = sa.index16 + 2
+	}
+	if sa.index1 == sa.index16 && sa.bitOffset1 == 0 {
+		sa.index1 = newIndex16
+	}
+	if sa.index8 == sa.index16 {
+		sa.index8 = newIndex16
+	}
+	if sa.index32 == sa.index16 {
+		if newIndex16&0x3 == 0 {
+			sa.index32 = newIndex16
+		} else {
+			sa.index32 = newIndex16 + (4 - (newIndex16 & 0x3))
+		}
+	}
+	if sa.index64 == sa.index16 {
+		if newIndex16&0x7 == 0 {
+			sa.index64 = newIndex16
+		} else {
+			sa.index64 = newIndex16 + (8 - (newIndex16 & 0x7))
+		}
+	}
+	sa.index16 = newIndex16
+}
+func (sa *structOffsetComputation) next32() {
+	var newIndex32 uint32
+	if sa.index32 != sa.index64 {
+		newIndex32 = sa.index64
+	} else {
+		newIndex32 = sa.index32 + 4
+	}
+	if sa.index1 == sa.index32 && sa.bitOffset1 == 0 {
+		sa.index1 = newIndex32
+	}
+	if sa.index8 == sa.index32 {
+		sa.index8 = newIndex32
+	}
+	if sa.index16 == sa.index32 {
+		sa.index16 = newIndex32
+	}
+	if sa.index64 == sa.index32 {
+		if newIndex32&0x7 == 0 {
+			sa.index64 = newIndex32
+		} else {
+			sa.index64 = newIndex32 + (8 - (newIndex32 & 0x7))
+		}
+	}
+	sa.index32 = newIndex32
+}
+func (sa *structOffsetComputation) next64() {
+	newIndex64 := sa.index64 + 8
+
+	if sa.index1 == sa.index64 && sa.bitOffset1 == 0 {
+		sa.index1 = newIndex64
+	}
+	if sa.index8 == sa.index64 {
+		sa.index8 = newIndex64
+	}
+	if sa.index16 == sa.index64 {
+		sa.index16 = newIndex64
+	}
+	if sa.index32 == sa.index64 {
+		sa.index32 = newIndex64
+	}
+	sa.index64 = newIndex64
+}
diff --git a/go/src/v.io/mojo/transcoder/target.go b/go/src/v.io/mojo/transcoder/target.go
new file mode 100644
index 0000000..cfb26f5
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/target.go
@@ -0,0 +1,213 @@
+package mojovdl
+
+import (
+	"encoding/binary"
+	"fmt"
+	"math"
+
+	"v.io/v23/vdl"
+)
+
+type target struct {
+	currentBitOffset uint8
+	current          bytesRef
+}
+
+func (t target) allocator() *allocator {
+	return t.current.allocator
+}
+
+func (t target) FromBool(src bool, tt *vdl.Type) error {
+	if src {
+		t.current.Bytes()[0] |= 1 << t.currentBitOffset
+	}
+	// shouldn't have to do anything for false
+	return nil
+}
+func (t target) FromUint(src uint64, tt *vdl.Type) error {
+	switch tt.Kind() {
+	case vdl.Byte:
+		t.current.Bytes()[0] = byte(src)
+	case vdl.Uint16:
+		binary.LittleEndian.PutUint16(t.current.Bytes(), uint16(src))
+	case vdl.Uint32:
+		binary.LittleEndian.PutUint32(t.current.Bytes(), uint32(src))
+	case vdl.Uint64:
+		binary.LittleEndian.PutUint64(t.current.Bytes(), src)
+	default:
+		return fmt.Errorf("invalid FromUint(%v, %v)", src, tt)
+	}
+	return nil
+}
+func (t target) FromInt(src int64, tt *vdl.Type) error {
+	switch tt.Kind() {
+	case vdl.Int16:
+		binary.LittleEndian.PutUint16(t.current.Bytes(), uint16(src))
+	case vdl.Int32:
+		binary.LittleEndian.PutUint32(t.current.Bytes(), uint32(src))
+	case vdl.Int64:
+		binary.LittleEndian.PutUint64(t.current.Bytes(), uint64(src))
+	default:
+		return fmt.Errorf("invalid FromInt(%v, %v)", src, tt)
+	}
+	return nil
+}
+func (t target) FromFloat(src float64, tt *vdl.Type) error {
+	switch tt.Kind() {
+	case vdl.Float32:
+		binary.LittleEndian.PutUint32(t.current.Bytes(), math.Float32bits(float32(src)))
+	case vdl.Float64:
+		binary.LittleEndian.PutUint64(t.current.Bytes(), math.Float64bits(src))
+	default:
+		return fmt.Errorf("invalid FromFloat(%v, %v)", src, tt)
+	}
+	return nil
+}
+func (t target) FromComplex(src complex128, tt *vdl.Type) error {
+	panic("UNIMPLEMENTED")
+}
+func (t target) writeBytes(src []byte) {
+	block := t.allocator().Allocate(uint32(len(src)), uint32(len(src)))
+	t.writePointer(block)
+	copy(block.Bytes(), src)
+}
+func (t target) FromBytes(src []byte, tt *vdl.Type) error {
+	t.writeBytes(src)
+	return nil
+}
+func (t target) FromString(src string, tt *vdl.Type) error {
+	t.writeBytes([]byte(src))
+	return nil
+}
+func (t target) FromEnumLabel(src string, tt *vdl.Type) error {
+	// enums in mojo are treated as an int32 on the wire (but have gaps in their values).
+	// This implementation assumes that we will use generated VDL values and not have gaps.
+	index := tt.EnumIndex(src)
+	binary.LittleEndian.PutUint32(t.current.Bytes(), uint32(index))
+	return nil
+}
+func (t target) FromTypeObject(src *vdl.Type) error {
+	panic("UNIMPLEMENTED")
+
+}
+func (t target) FromNil(tt *vdl.Type) error {
+	switch tt.Kind() {
+	case vdl.Optional:
+		elemType := tt.Elem()
+		switch elemType.Kind() {
+		case vdl.Union, vdl.Struct: // Array? String? Bytes? List? Set?
+			// Note: for union, this zeros 16 bytes, but for others it does just 8.
+			zeroBytes(t.current.Bytes())
+		default:
+			panic(fmt.Sprintf("Vdl type %v cannot be optional", tt))
+		}
+	case vdl.Any:
+		panic("Any rep not yet determined")
+	default:
+		panic("Type cannot be nil")
+	}
+	return nil
+}
+func zeroBytes(dat []byte) {
+	copy(dat, make([]byte, len(dat)))
+}
+
+func (t target) StartList(tt *vdl.Type, len int) (vdl.ListTarget, error) {
+	if tt.Kind() == vdl.Optional {
+		tt = tt.Elem()
+	}
+	bitsNeeded := baseTypeSizeBits(tt.Elem()) * uint32(len)
+	block := t.allocator().Allocate((bitsNeeded+7)/8, uint32(len))
+	t.writePointer(block)
+	if tt.Elem().Kind() == vdl.Bool {
+		return &bitListTarget{
+			block: block,
+		}, nil
+	} else {
+		return &listTarget{
+			incrementSize: baseTypeSizeBits(tt.Elem()) / 8,
+			block:         block,
+		}, nil
+	}
+}
+func (t target) FinishList(x vdl.ListTarget) error {
+	return nil
+}
+
+// TODO(bprosnitz) This uses list, should we use map instead?
+func (t target) StartSet(tt *vdl.Type, len int) (vdl.SetTarget, error) {
+	if tt.Kind() == vdl.Optional {
+		tt = tt.Elem()
+	}
+	bitsNeeded := baseTypeSizeBits(tt.Key()) * uint32(len)
+	block := t.allocator().Allocate((bitsNeeded+7)/8, uint32(len))
+	t.writePointer(block)
+	if tt.Key().Kind() == vdl.Bool {
+		return &bitListTarget{
+			block: block,
+		}, nil
+	} else {
+		return &listTarget{
+			incrementSize: baseTypeSizeBits(tt.Key()) / 8,
+			block:         block,
+		}, nil
+	}
+}
+func (t target) FinishSet(x vdl.SetTarget) error {
+	return nil
+}
+func (t target) StartMap(tt *vdl.Type, len int) (vdl.MapTarget, error) {
+	if tt.Kind() == vdl.Optional {
+		tt = tt.Elem()
+	}
+	pointerBlock := t.allocator().Allocate(16, 0)
+	t.writePointer(pointerBlock)
+
+	st := target{
+		current: pointerBlock.Slice(0, 8),
+	}
+	setTarget, err := st.StartSet(vdl.SetType(tt.Key()), len)
+	if err != nil {
+		return nil, err
+	}
+	lt := target{
+		current: pointerBlock.Slice(8, 16),
+	}
+	listTarget, err := lt.StartList(vdl.ListType(tt.Elem()), len)
+	if err != nil {
+		return nil, err
+	}
+	return &mapTarget{
+		setTarget:  setTarget,
+		listTarget: listTarget,
+	}, nil
+}
+func (t target) FinishMap(x vdl.MapTarget) error {
+	return nil
+}
+func (t target) StartFields(tt *vdl.Type) (vdl.FieldsTarget, error) {
+	if tt.Kind() == vdl.Optional {
+		tt = tt.Elem()
+	}
+	if tt.Kind() == vdl.Union {
+		return unionFieldsTarget{
+			vdlType: tt,
+			block:   t.current,
+		}, nil
+	}
+	block := t.allocator().Allocate(neededStructAllocationSize(tt), 0)
+	t.writePointer(block)
+	return fieldsTarget{
+			vdlType: tt,
+			block:   block,
+		},
+		nil
+}
+func (t target) FinishFields(x vdl.FieldsTarget) error {
+	return nil
+}
+
+func (t target) writePointer(alloc bytesRef) {
+	offset := alloc.AsPointer(t.current)
+	binary.LittleEndian.PutUint64(t.current.Bytes(), uint64(offset))
+}
diff --git a/go/src/v.io/mojo/transcoder/type.go b/go/src/v.io/mojo/transcoder/type.go
new file mode 100644
index 0000000..3fc7c35
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/type.go
@@ -0,0 +1,265 @@
+package mojovdl
+
+import (
+	"fmt"
+
+	"mojo/public/interfaces/bindings/mojom_types"
+
+	"v.io/v23/vdl"
+)
+
+/*// Given a descriptor mapping, produce 2 maps.
+// The former maps from mojom identifiers to VDL Type.
+// The latter maps from VDL Type string (hash cons) to the mojom identifier.
+// These maps are used to interconvert more easily.
+func AnalyzeMojomDescriptors(mp map[string]mojom_types.UserDefinedType) map[string]*vdl.Type {
+	m2V := make(map[string]*vdl.Type)
+	for s, udt := range mp {
+		m2V[s] = mojomToVDLTypeUDT(udt, mp)
+	}
+	return m2V
+}*/
+
+// Convert the known type reference to a vdl type.
+// Panics if the type reference was not known.
+/*func TypeReferenceToVDLType(tr mojom_types.TypeReference, mp map[string]mojom_types.UserDefinedType) *vdl.Type {
+	if udt, ok := mp[tr.TypeKey]; ok {
+		return mojomToVDLTypeUDT(udt, mp)
+	}
+	panic("Type Key %s was not present in the mapping", tr.typeKey)
+}*/
+
+func mojomToVDLTypeUDT(udt mojom_types.UserDefinedType, mp map[string]mojom_types.UserDefinedType) (vt *vdl.Type) {
+	u := interface{}(udt)
+	switch u := u.(type) { // To do the type switch, udt has to be converted to interface{}.
+	case *mojom_types.UserDefinedTypeEnumType: // enum
+		me := u.Value
+
+		// TODO: Assumes that the maximum enum index is len(me.Values) - 1.
+		labels := make([]string, len(me.Values))
+		for _, ev := range me.Values { // per EnumValue...
+			// EnumValue contains a ConstantOccurrence
+			// ConstantOccurrence contains a ConstantValue
+			// ConstantValue is a union that contains an EnumConstantValue
+			ecv := ev.Value.Value.(*mojom_types.ConstantValueEnumValue).Value
+
+			// EnumConstantValue contains the EnumValueName and IntValue
+			labels[int(ecv.IntValue)] = *ecv.EnumValueName
+		}
+
+		vt = vdl.NamedType(*me.DeclData.ShortName, vdl.EnumType(labels...))
+	case *mojom_types.UserDefinedTypeStructType: // struct
+		ms := u.Value
+
+		vt = MojomStructToVDLType(ms, mp)
+	case *mojom_types.UserDefinedTypeUnionType: // union
+		mu := u.Value
+
+		vfields := make([]vdl.Field, len(mu.Fields))
+		for ix, mfield := range mu.Fields {
+			vfields[ix] = vdl.Field{
+				Name: *mfield.DeclData.ShortName,
+				Type: MojomToVDLType(mfield.Type, mp),
+			}
+		}
+		vt = vdl.NamedType(*mu.DeclData.ShortName, vdl.UnionType(vfields...))
+	case *mojom_types.UserDefinedTypeInterfaceType: // interface
+		panic("interfaces don't exist in vdl")
+	default: // unknown
+		panic(fmt.Errorf("user defined type %#v with unknown tag %d", udt, udt.Tag()))
+	}
+	return vt
+}
+
+func MojomStructToVDLType(ms mojom_types.MojomStruct, mp map[string]mojom_types.UserDefinedType) (vt *vdl.Type) {
+	vfields := make([]vdl.Field, len(ms.Fields))
+	for ix, mfield := range ms.Fields {
+		vfields[ix] = vdl.Field{
+			Name: *mfield.DeclData.ShortName,
+			Type: MojomToVDLType(mfield.FieldType, mp),
+		}
+	}
+	vt = vdl.NamedType(*ms.DeclData.ShortName, vdl.StructType(vfields...))
+	return vt
+}
+
+// Given a mojom Type and the descriptor mapping, produce the corresponding vdltype.
+func MojomToVDLType(mojomtype mojom_types.Type, mp map[string]mojom_types.UserDefinedType) (vt *vdl.Type) {
+	// TODO(alexfandrianto): Cyclic types?
+	mt := interface{}(mojomtype)
+	switch mt := interface{}(mt).(type) { // To do the type switch, mt has to be converted to interface{}.
+	case *mojom_types.TypeSimpleType: // TypeSimpleType
+		switch mt.Value {
+		case mojom_types.SimpleType_Bool:
+			vt = vdl.BoolType
+		case mojom_types.SimpleType_Double:
+			vt = vdl.BoolType
+		case mojom_types.SimpleType_Float:
+			vt = vdl.BoolType
+		case mojom_types.SimpleType_InT8:
+			panic("int8 doesn't exist in vdl")
+		case mojom_types.SimpleType_InT16:
+			vt = vdl.Int16Type
+		case mojom_types.SimpleType_InT32:
+			vt = vdl.Int32Type
+		case mojom_types.SimpleType_InT64:
+			vt = vdl.Int64Type
+		case mojom_types.SimpleType_UinT8:
+			vt = vdl.ByteType
+		case mojom_types.SimpleType_UinT16:
+			vt = vdl.Uint16Type
+		case mojom_types.SimpleType_UinT32:
+			vt = vdl.Uint32Type
+		case mojom_types.SimpleType_UinT64:
+			vt = vdl.Uint64Type
+		}
+	case *mojom_types.TypeStringType: // TypeStringType
+		st := mt.Value
+		if st.Nullable {
+			panic("nullable strings don't exist in vdl")
+		}
+		vt = vdl.StringType
+	case *mojom_types.TypeArrayType: // TypeArrayType
+		at := mt.Value
+		if at.Nullable {
+			panic("nullable arrays don't exist in vdl")
+		}
+		if at.FixedLength > 0 {
+			vt = vdl.ArrayType(int(at.FixedLength), MojomToVDLType(at.ElementType, mp))
+		} else {
+			vt = vdl.ListType(MojomToVDLType(at.ElementType, mp))
+		}
+	case *mojom_types.TypeMapType: // TypeMapType
+		// Note that mojom doesn't have sets.
+		m := mt.Value
+		if m.Nullable {
+			panic("nullable maps don't exist in vdl")
+		}
+		vt = vdl.MapType(MojomToVDLType(m.KeyType, mp), MojomToVDLType(m.ValueType, mp))
+	case *mojom_types.TypeHandleType: // TypeHandleType
+		panic("handles don't exist in vdl")
+	case *mojom_types.TypeTypeReference: // TypeTypeReference
+		tr := mt.Value
+		if tr.IsInterfaceRequest {
+			panic("interface requests don't exist in vdl")
+		}
+		udt := mp[*tr.TypeKey]
+		if udt.Tag() != 1 && tr.Nullable {
+			panic("nullable non-struct type reference cannot be represented in vdl")
+		}
+		vt = mojomToVDLTypeUDT(udt, mp)
+	default:
+		panic(fmt.Errorf("%#v has unknown tag %d", mojomtype, mojomtype.Tag()))
+	}
+
+	return vt
+}
+
+/*func V2M(vt *vdl.Type, v2M map[string]string) mojom_types.Type {
+	if m, ok := v2M[vt.String()]; ok {
+		return mojom_types.TypeTypeReference{
+			Value: mojom_types.TypeReference{
+				Nullable:   nullable,
+				Identifier: m,
+				TypeKey:    m,
+			},
+		}
+	}
+	panic("vdl type %#v was not present in the mapping", vt)
+}
+
+// From the vdltype and the reverse mapping of the descriptor (hashcons vdltype string => typekey),
+// produce the corresponding mojom Type.
+func VDLToMojomType(vt *vdl.Type, v2M map[string]string) mojom_types.Type {
+	return vdlToMojomTypeImpl(vt, v2M, false)
+}
+
+func vdlToMojomTypeImpl(vt *vdl.Type, v2M map[string]string, bool nullable) mojom_types.Type {
+	if m, ok := v2M[vt.String()]; ok {
+		return mojom_types.TypeTypeReference{
+			Value: mojom_types.TypeReference{
+				Nullable:   nullable,
+				Identifier: m,
+				TypeKey:    m,
+			},
+		}
+	}
+
+	fmt.Println("Missed the vdl to mojom map")
+	// In the unlikely case where v2M was insufficient, we have the remaining logic.
+
+	switch vt.Kind() {
+	case vdl.Bool:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_Bool}
+	case vdl.Byte:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_UinT8}
+	case vdl.Uint16:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_UinT16}
+	case vdl.Uint32:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_UinT32}
+	case vdl.Uint64:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_UinT64}
+	case vdl.Int16:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_InT16}
+	case vdl.Int32:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_InT32}
+	case vdl.Int64:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_InT64}
+	case vdl.Float32:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_Float}
+	case vdl.Float64:
+		return mojom_types.TypeSimpleType{Value: mojom_types.SimpleType_Double}
+	case vdl.Complex64:
+		panic("complex float doesn't exist in mojom")
+	case vdl.Complex128:
+		panic("complex double doesn't exist in mojom")
+	case vdl.String:
+		return mojom_types.TypeStringType{Value: mojom_types.StringType{}}
+	case vdl.Array:
+		elemType := VDLToMojomType(vt.Elem(), v2M)
+		return mojom_types.TypeArrayType{
+			Value: mojom_types.ArrayType{
+				FixedLength: int64(vt.Len()),
+				ElementType: elemType,
+			},
+		}
+	case vdl.List:
+		elemType := VDLToMojomType(vt.Elem(), v2M)
+		return mojom_types.TypeArrayType{
+			Value: mojom_types.ArrayType{
+				FixedLength: -1,
+				ElementType: elemType,
+			},
+		}
+	case vdl.Set:
+		panic("set doesn't exist in mojom")
+	case vdl.Map:
+		keyType := VDLToMojomType(vt.Key(), v2M)
+		elemType := VDLToMojomType(vt.Elem(), v2M)
+		return mojom_types.TypeMapType{
+			Value: mojom_types.MapType{
+				KeyType:   &keyType,
+				ValueType: &elemType,
+			},
+		}
+	case vdl.Struct, vdl.Union, vdl.Enum:
+		mt := mojom_types.TypeTypeReference{
+			Value: mojom_types.TypeReference{
+				Nullable:   nullable,
+				Identifier: v2M[vt.String()],
+				TypeKey:    v2M[vt.String()],
+			},
+		}
+		return mt
+	case vdl.TypeObject:
+		panic("typeobject doesn't exist in mojom")
+	case vdl.Any:
+		panic("any doesn't exist in mojom")
+	case vdl.Optional:
+		// TODO(alexfandrianto): Unfortunately, without changing vdl, we can only
+		// manage optional (named) structs. This doesn't Nullify anything else.
+		return vdlToMojomTypeImpl(vt.Elem(), v2M, true)
+	}
+	panic(fmt.Errorf("%v can't be converted to MojomType", vt))
+}
+*/
diff --git a/go/src/v.io/mojo/transcoder/typed_targets.go b/go/src/v.io/mojo/transcoder/typed_targets.go
new file mode 100644
index 0000000..d09160e
--- /dev/null
+++ b/go/src/v.io/mojo/transcoder/typed_targets.go
@@ -0,0 +1,123 @@
+package mojovdl
+
+import (
+	"encoding/binary"
+
+	"v.io/v23/vdl"
+)
+
+// for struct
+type fieldsTarget struct {
+	vdlType *vdl.Type
+	block   bytesRef
+}
+
+func (fe fieldsTarget) StartField(name string) (key, field vdl.Target, _ error) {
+	fieldType, fieldIndex := fe.vdlType.FieldByName(name)
+	byteOffset, bitOffset := offsetInStruct(fieldIndex, fe.vdlType)
+	numBits := baseTypeSizeBits(fieldType.Type)
+	refSize := (numBits + 7) / 8
+	newRef := fe.block.Slice(byteOffset, byteOffset+refSize)
+	return nil, target{
+		currentBitOffset: bitOffset,
+		current:          newRef,
+	}, nil
+}
+func (fieldsTarget) FinishField(key, field vdl.Target) error {
+	return nil
+}
+
+type unionFieldsTarget struct {
+	vdlType *vdl.Type
+	block   bytesRef
+}
+
+func (ufe unionFieldsTarget) StartField(name string) (key, field vdl.Target, _ error) {
+	fld, index := ufe.vdlType.FieldByName(name)
+	binary.LittleEndian.PutUint32(ufe.block.Bytes(), 16)
+	binary.LittleEndian.PutUint32(ufe.block.Bytes()[4:], uint32(index))
+
+	valueSlice := ufe.block.Slice(8, 16)
+	if fld.Type.Kind() == vdl.Union {
+		// nested union, create a pointer to the body
+		nestedUnionBlock := ufe.block.allocator.Allocate(8, 0)
+		offset := nestedUnionBlock.AsPointer(valueSlice)
+		binary.LittleEndian.PutUint64(valueSlice.Bytes(), uint64(offset))
+		return nil, target{
+			currentBitOffset: 0,
+			current:          nestedUnionBlock.SignedSlice(-8, 8),
+		}, nil
+	}
+	return nil, target{
+		currentBitOffset: 0,
+		current:          valueSlice,
+	}, nil
+}
+func (unionFieldsTarget) FinishField(key, field vdl.Target) error {
+	return nil
+}
+
+// doubles as set target
+type listTarget struct {
+	incrementSize uint32
+	block         bytesRef
+	nextPosition  uint32
+}
+
+func (lt *listTarget) StartElem(index int) (elem vdl.Target, _ error) {
+	// TODO(bprosnitz) Index is ignored -- we should probably remove this from Target.
+	sliceBlock := lt.block.Slice(lt.nextPosition, lt.nextPosition+lt.incrementSize)
+	lt.nextPosition += lt.incrementSize
+	return target{
+		current: sliceBlock,
+	}, nil
+}
+func (lt *listTarget) StartKey() (key vdl.Target, _ error) {
+	return lt.StartElem(0)
+}
+func (listTarget) FinishElem(elem vdl.Target) error {
+	return nil
+}
+func (listTarget) FinishKey(key vdl.Target) error {
+	return nil
+}
+
+type bitListTarget struct {
+	block           bytesRef
+	nextBitPosition uint32
+}
+
+func (blt *bitListTarget) StartElem(index int) (elem vdl.Target, _ error) {
+	bitPos := blt.nextBitPosition
+	blt.nextBitPosition++
+	byteIndex := bitPos / 8
+	sliceBlock := blt.block.Slice(byteIndex, byteIndex+1)
+	return target{
+		currentBitOffset: uint8(bitPos % 8),
+		current:          sliceBlock,
+	}, nil
+}
+func (blt *bitListTarget) StartKey() (key vdl.Target, _ error) {
+	return blt.StartElem(0)
+}
+func (bitListTarget) FinishElem(elem vdl.Target) error {
+	return nil
+}
+func (bitListTarget) FinishKey(key vdl.Target) error {
+	return nil
+}
+
+type mapTarget struct {
+	listTarget vdl.ListTarget
+	setTarget  vdl.SetTarget
+}
+
+func (mt *mapTarget) StartKey() (key vdl.Target, _ error) {
+	return mt.setTarget.StartKey()
+}
+func (mt *mapTarget) FinishKeyStartField(key vdl.Target) (field vdl.Target, _ error) {
+	return mt.listTarget.StartElem(0)
+}
+func (mapTarget) FinishField(key, field vdl.Target) error {
+	return nil
+}
