// encode serializes msg and prepends the message header. If msg is nil, it // generates the message header of 0 message length. func encode(c grpc.Codec, msg interface{}, cp grpc.Compressor, cbuf *bytes.Buffer) ([]byte, error) { var b []byte var length uint if msg != nil { var err error // TODO(zhaoq): optimize to reduce memory alloc and copying. b, err = c.Marshal(msg) if err != nil { return nil, err } if cp != nil { if err := cp.Do(cbuf, b); err != nil { return nil, err } b = cbuf.Bytes() } length = uint(len(b)) } if length > math.MaxUint32 { return nil, Errorf(codes.InvalidArgument, "grpc: message too large (%d bytes)", length) } const ( payloadLen = 1 sizeLen = 4 ) var buf = make([]byte, payloadLen+sizeLen+len(b)) // Write payload format if cp == nil { buf[0] = byte(compressionNone) } else { buf[0] = byte(compressionMade) } // Write length of b into buf binary.BigEndian.PutUint32(buf[1:], uint32(length)) // Copy encoded msg to buf copy(buf[5:], b) return buf, nil }