func (p *pipeTransport) SendMessage(ctx context.Context, msg rpccapnp.Message) error {
	if !p.startSend() {
		return errClosed
	}
	defer p.finishSend()

	buf, err := msg.Segment().Message().Marshal()
	if err != nil {
		return err
	}
	mm, err := capnp.Unmarshal(buf)
	if err != nil {
		return err
	}
	msg, err = rpccapnp.ReadRootMessage(mm)
	if err != nil {
		return err
	}

	select {
	case p.w <- msg:
		return nil
	case <-ctx.Done():
		return ctx.Err()
	case <-p.finish:
		return errClosed
	case <-p.otherFin:
		return errBrokenPipe
	}
}
Beispiel #2
0
// copyRPCMessage clones an RPC packet.
func copyRPCMessage(m rpccapnp.Message) rpccapnp.Message {
	mm := copyMessage(m.Segment().Message())
	rpcMsg, err := rpccapnp.ReadRootMessage(mm)
	if err != nil {
		panic(err)
	}
	return rpcMsg
}
Beispiel #3
0
func (s *streamTransport) RecvMessage(ctx context.Context) (rpccapnp.Message, error) {
	var (
		msg *capnp.Message
		err error
	)
	read := make(chan struct{})
	go func() {
		msg, err = s.dec.Decode()
		close(read)
	}()
	select {
	case <-read:
	case <-ctx.Done():
		return rpccapnp.Message{}, ctx.Err()
	}
	if err != nil {
		return rpccapnp.Message{}, err
	}
	return rpccapnp.ReadRootMessage(msg)
}
func (p *pipeTransport) RecvMessage(ctx context.Context) (rpccapnp.Message, error) {
	// Scribble over shared buffer to test for race conditions.
	for b, i := p.rbuf.Bytes(), 0; i < len(b); i++ {
		b[i] = 0xff
	}
	p.rbuf.Reset()

	select {
	case msg, ok := <-p.r:
		if !ok {
			return rpccapnp.Message{}, errBrokenPipe
		}
		if err := capnp.NewEncoder(&p.rbuf).Encode(msg.Segment().Message()); err != nil {
			return rpccapnp.Message{}, err
		}
		m, err := capnp.Unmarshal(p.rbuf.Bytes())
		if err != nil {
			return rpccapnp.Message{}, err
		}
		return rpccapnp.ReadRootMessage(m)
	case <-ctx.Done():
		return rpccapnp.Message{}, ctx.Err()
	}
}