xref: /aosp_15_r20/external/protobuf/benchmarks/go/go_benchmark_test.go (revision 1b3f573f81763fcece89efc2b6a5209149e44ab8)
1*1b3f573fSAndroid Build Coastguard Workerpackage main
2*1b3f573fSAndroid Build Coastguard Worker
3*1b3f573fSAndroid Build Coastguard Workerimport (
4*1b3f573fSAndroid Build Coastguard Worker	benchmarkWrapper "../tmp"
5*1b3f573fSAndroid Build Coastguard Worker	googleMessage1Proto2 "../tmp/datasets/google_message1/proto2"
6*1b3f573fSAndroid Build Coastguard Worker	googleMessage1Proto3 "../tmp/datasets/google_message1/proto3"
7*1b3f573fSAndroid Build Coastguard Worker	googleMessage2 "../tmp/datasets/google_message2"
8*1b3f573fSAndroid Build Coastguard Worker	googleMessage3 "../tmp/datasets/google_message3"
9*1b3f573fSAndroid Build Coastguard Worker	googleMessage4 "../tmp/datasets/google_message4"
10*1b3f573fSAndroid Build Coastguard Worker	"flag"
11*1b3f573fSAndroid Build Coastguard Worker	"github.com/golang/protobuf/proto"
12*1b3f573fSAndroid Build Coastguard Worker	"io/ioutil"
13*1b3f573fSAndroid Build Coastguard Worker	"testing"
14*1b3f573fSAndroid Build Coastguard Worker)
15*1b3f573fSAndroid Build Coastguard Worker
16*1b3f573fSAndroid Build Coastguard Worker// Data is returned by the Load function.
17*1b3f573fSAndroid Build Coastguard Workertype Dataset struct {
18*1b3f573fSAndroid Build Coastguard Worker	name        string
19*1b3f573fSAndroid Build Coastguard Worker	newMessage  func() proto.Message
20*1b3f573fSAndroid Build Coastguard Worker	marshaled   [][]byte
21*1b3f573fSAndroid Build Coastguard Worker	unmarshaled []proto.Message
22*1b3f573fSAndroid Build Coastguard Worker}
23*1b3f573fSAndroid Build Coastguard Worker
24*1b3f573fSAndroid Build Coastguard Workervar datasets []Dataset
25*1b3f573fSAndroid Build Coastguard Worker
26*1b3f573fSAndroid Build Coastguard Worker// This is used to getDefaultInstance for a message type.
27*1b3f573fSAndroid Build Coastguard Workerfunc generateNewMessageFunction(dataset benchmarkWrapper.BenchmarkDataset) func() proto.Message {
28*1b3f573fSAndroid Build Coastguard Worker	switch dataset.MessageName {
29*1b3f573fSAndroid Build Coastguard Worker	case "benchmarks.proto3.GoogleMessage1":
30*1b3f573fSAndroid Build Coastguard Worker		return func() proto.Message { return new(googleMessage1Proto3.GoogleMessage1) }
31*1b3f573fSAndroid Build Coastguard Worker	case "benchmarks.proto2.GoogleMessage1":
32*1b3f573fSAndroid Build Coastguard Worker		return func() proto.Message { return new(googleMessage1Proto2.GoogleMessage1) }
33*1b3f573fSAndroid Build Coastguard Worker	case "benchmarks.proto2.GoogleMessage2":
34*1b3f573fSAndroid Build Coastguard Worker		return func() proto.Message { return new(googleMessage2.GoogleMessage2) }
35*1b3f573fSAndroid Build Coastguard Worker	case "benchmarks.google_message3.GoogleMessage3":
36*1b3f573fSAndroid Build Coastguard Worker		return func() proto.Message { return new(googleMessage3.GoogleMessage3) }
37*1b3f573fSAndroid Build Coastguard Worker	case "benchmarks.google_message4.GoogleMessage4":
38*1b3f573fSAndroid Build Coastguard Worker		return func() proto.Message { return new(googleMessage4.GoogleMessage4) }
39*1b3f573fSAndroid Build Coastguard Worker	default:
40*1b3f573fSAndroid Build Coastguard Worker		panic("Unknown message type: " + dataset.MessageName)
41*1b3f573fSAndroid Build Coastguard Worker	}
42*1b3f573fSAndroid Build Coastguard Worker}
43*1b3f573fSAndroid Build Coastguard Worker
44*1b3f573fSAndroid Build Coastguard Workerfunc init() {
45*1b3f573fSAndroid Build Coastguard Worker	flag.Parse()
46*1b3f573fSAndroid Build Coastguard Worker	for _, f := range flag.Args() {
47*1b3f573fSAndroid Build Coastguard Worker		// Load the benchmark.
48*1b3f573fSAndroid Build Coastguard Worker		b, err := ioutil.ReadFile(f)
49*1b3f573fSAndroid Build Coastguard Worker		if err != nil {
50*1b3f573fSAndroid Build Coastguard Worker			panic(err)
51*1b3f573fSAndroid Build Coastguard Worker		}
52*1b3f573fSAndroid Build Coastguard Worker
53*1b3f573fSAndroid Build Coastguard Worker		// Parse the benchmark.
54*1b3f573fSAndroid Build Coastguard Worker		var dm benchmarkWrapper.BenchmarkDataset
55*1b3f573fSAndroid Build Coastguard Worker		if err := proto.Unmarshal(b, &dm); err != nil {
56*1b3f573fSAndroid Build Coastguard Worker			panic(err)
57*1b3f573fSAndroid Build Coastguard Worker		}
58*1b3f573fSAndroid Build Coastguard Worker
59*1b3f573fSAndroid Build Coastguard Worker		// Determine the concrete protobuf message type to use.
60*1b3f573fSAndroid Build Coastguard Worker		var ds Dataset
61*1b3f573fSAndroid Build Coastguard Worker		ds.newMessage = generateNewMessageFunction(dm)
62*1b3f573fSAndroid Build Coastguard Worker
63*1b3f573fSAndroid Build Coastguard Worker		// Unmarshal each test message.
64*1b3f573fSAndroid Build Coastguard Worker		for _, payload := range dm.Payload {
65*1b3f573fSAndroid Build Coastguard Worker			ds.marshaled = append(ds.marshaled, payload)
66*1b3f573fSAndroid Build Coastguard Worker			m := ds.newMessage()
67*1b3f573fSAndroid Build Coastguard Worker			if err := proto.Unmarshal(payload, m); err != nil {
68*1b3f573fSAndroid Build Coastguard Worker				panic(err)
69*1b3f573fSAndroid Build Coastguard Worker			}
70*1b3f573fSAndroid Build Coastguard Worker			ds.unmarshaled = append(ds.unmarshaled, m)
71*1b3f573fSAndroid Build Coastguard Worker		}
72*1b3f573fSAndroid Build Coastguard Worker		ds.name = f
73*1b3f573fSAndroid Build Coastguard Worker
74*1b3f573fSAndroid Build Coastguard Worker		datasets = append(datasets, ds)
75*1b3f573fSAndroid Build Coastguard Worker	}
76*1b3f573fSAndroid Build Coastguard Worker}
77*1b3f573fSAndroid Build Coastguard Worker
78*1b3f573fSAndroid Build Coastguard Workerfunc Benchmark(b *testing.B) {
79*1b3f573fSAndroid Build Coastguard Worker	for _, ds := range datasets {
80*1b3f573fSAndroid Build Coastguard Worker		b.Run(ds.name, func(b *testing.B) {
81*1b3f573fSAndroid Build Coastguard Worker			b.Run("Unmarshal", func(b *testing.B) {
82*1b3f573fSAndroid Build Coastguard Worker				for i := 0; i < b.N; i++ {
83*1b3f573fSAndroid Build Coastguard Worker					for j, payload := range ds.marshaled {
84*1b3f573fSAndroid Build Coastguard Worker						out := ds.newMessage()
85*1b3f573fSAndroid Build Coastguard Worker						if err := proto.Unmarshal(payload, out); err != nil {
86*1b3f573fSAndroid Build Coastguard Worker							b.Fatalf("can't unmarshal message %d %v", j, err)
87*1b3f573fSAndroid Build Coastguard Worker						}
88*1b3f573fSAndroid Build Coastguard Worker					}
89*1b3f573fSAndroid Build Coastguard Worker				}
90*1b3f573fSAndroid Build Coastguard Worker			})
91*1b3f573fSAndroid Build Coastguard Worker			b.Run("Marshal", func(b *testing.B) {
92*1b3f573fSAndroid Build Coastguard Worker				for i := 0; i < b.N; i++ {
93*1b3f573fSAndroid Build Coastguard Worker					for j, m := range ds.unmarshaled {
94*1b3f573fSAndroid Build Coastguard Worker						if _, err := proto.Marshal(m); err != nil {
95*1b3f573fSAndroid Build Coastguard Worker							b.Fatalf("can't marshal message %d %+v: %v", j, m, err)
96*1b3f573fSAndroid Build Coastguard Worker						}
97*1b3f573fSAndroid Build Coastguard Worker					}
98*1b3f573fSAndroid Build Coastguard Worker				}
99*1b3f573fSAndroid Build Coastguard Worker			})
100*1b3f573fSAndroid Build Coastguard Worker			b.Run("Size", func(b *testing.B) {
101*1b3f573fSAndroid Build Coastguard Worker				for i := 0; i < b.N; i++ {
102*1b3f573fSAndroid Build Coastguard Worker					for _, m := range ds.unmarshaled {
103*1b3f573fSAndroid Build Coastguard Worker						proto.Size(m)
104*1b3f573fSAndroid Build Coastguard Worker					}
105*1b3f573fSAndroid Build Coastguard Worker				}
106*1b3f573fSAndroid Build Coastguard Worker			})
107*1b3f573fSAndroid Build Coastguard Worker			b.Run("Clone", func(b *testing.B) {
108*1b3f573fSAndroid Build Coastguard Worker				for i := 0; i < b.N; i++ {
109*1b3f573fSAndroid Build Coastguard Worker					for _, m := range ds.unmarshaled {
110*1b3f573fSAndroid Build Coastguard Worker						proto.Clone(m)
111*1b3f573fSAndroid Build Coastguard Worker					}
112*1b3f573fSAndroid Build Coastguard Worker				}
113*1b3f573fSAndroid Build Coastguard Worker			})
114*1b3f573fSAndroid Build Coastguard Worker			b.Run("Merge", func(b *testing.B) {
115*1b3f573fSAndroid Build Coastguard Worker				for i := 0; i < b.N; i++ {
116*1b3f573fSAndroid Build Coastguard Worker					for _, m := range ds.unmarshaled {
117*1b3f573fSAndroid Build Coastguard Worker						out := ds.newMessage()
118*1b3f573fSAndroid Build Coastguard Worker						proto.Merge(out, m)
119*1b3f573fSAndroid Build Coastguard Worker					}
120*1b3f573fSAndroid Build Coastguard Worker				}
121*1b3f573fSAndroid Build Coastguard Worker			})
122*1b3f573fSAndroid Build Coastguard Worker		})
123*1b3f573fSAndroid Build Coastguard Worker	}
124*1b3f573fSAndroid Build Coastguard Worker}
125