Implement bp2build converter for rust_protobuf_host

Test: go test
Bug: 295925256
Change-Id: I43b7359da8fc19f4338e2583448b7617194df5e6
diff --git a/bp2build/rust_protobuf_conversion_test.go b/bp2build/rust_protobuf_conversion_test.go
new file mode 100644
index 0000000..a779c36
--- /dev/null
+++ b/bp2build/rust_protobuf_conversion_test.go
@@ -0,0 +1,46 @@
+package bp2build
+
+import (
+	"android/soong/android"
+	"android/soong/rust"
+	"testing"
+)
+
+func runRustProtobufTestCase(t *testing.T, tc Bp2buildTestCase) {
+	t.Helper()
+	RunBp2BuildTestCase(t, registerRustProtobufModuleTypes, tc)
+}
+
+func registerRustProtobufModuleTypes(ctx android.RegistrationContext) {
+	ctx.RegisterModuleType("rust_protobuf_host", rust.RustProtobufHostFactory)
+
+}
+
+func TestRustProtobufHostTestCase(t *testing.T) {
+	runRustProtobufTestCase(t, Bp2buildTestCase{
+		Dir:       "external/rust/crates/foo",
+		Blueprint: "",
+		Filesystem: map[string]string{
+			"external/rust/crates/foo/src/lib.rs":    "",
+			"external/rust/crates/foo/src/helper.rs": "",
+			"external/rust/crates/foo/Android.bp": `
+rust_protobuf_host {
+	name: "libfoo",
+	crate_name: "foo",
+	protos: ["src/foo.proto"],
+    bazel_module: { bp2build_available: true },
+}
+`,
+		},
+		ExpectedBazelTargets: []string{
+			makeBazelTargetHostOrDevice("proto_library", "libfoo_proto", AttrNameToString{
+				"srcs": `["src/foo.proto"]`,
+			}, android.HostSupported),
+			makeBazelTargetHostOrDevice("rust_proto_library", "libfoo", AttrNameToString{
+				"crate_name": `"foo"`,
+				"deps":       `[":libfoo_proto"]`,
+			}, android.HostSupported),
+		},
+	},
+	)
+}
diff --git a/rust/protobuf.go b/rust/protobuf.go
index a14ebea..ae82844 100644
--- a/rust/protobuf.go
+++ b/rust/protobuf.go
@@ -19,6 +19,9 @@
 	"strings"
 
 	"android/soong/android"
+	"android/soong/bazel"
+
+	"github.com/google/blueprint/proptools"
 )
 
 var (
@@ -264,5 +267,71 @@
 
 	module := NewSourceProviderModule(hod, protobuf, false, false)
 
+	android.InitBazelModule(module)
+
 	return module, protobuf
 }
+
+type rustProtoAttributes struct {
+	Srcs       bazel.LabelListAttribute
+	Crate_name bazel.StringAttribute
+	Deps       bazel.LabelListAttribute
+}
+
+type protoLibraryAttributes struct {
+	Srcs bazel.LabelListAttribute
+}
+
+func protoLibraryBp2build(ctx android.TopDownMutatorContext, m *Module) {
+	var protoFiles []string
+
+	for _, propsInterface := range m.sourceProvider.SourceProviderProps() {
+		if possibleProps, ok := propsInterface.(*ProtobufProperties); ok {
+			protoFiles = possibleProps.Protos
+			break
+		}
+	}
+
+	protoLibraryName := m.Name() + "_proto"
+
+	protoDeps := bazel.LabelListAttribute{
+		Value: bazel.LabelList{
+			Includes: []bazel.Label{
+				{
+					Label:              ":" + protoLibraryName,
+					OriginalModuleName: m.Name(),
+				},
+			},
+		},
+	}
+
+	ctx.CreateBazelTargetModule(
+		bazel.BazelTargetModuleProperties{
+			Rule_class: "proto_library",
+		},
+		android.CommonAttributes{
+			Name: protoLibraryName,
+		},
+		&protoLibraryAttributes{
+			Srcs: bazel.MakeLabelListAttribute(
+				android.BazelLabelForModuleSrc(ctx, protoFiles),
+			),
+		},
+	)
+
+	ctx.CreateBazelTargetModule(
+		bazel.BazelTargetModuleProperties{
+			Rule_class:        "rust_proto_library",
+			Bzl_load_location: "@rules_rust//proto/protobuf:defs.bzl",
+		},
+		android.CommonAttributes{
+			Name: m.Name(),
+		},
+		&rustProtoAttributes{
+			Crate_name: bazel.StringAttribute{
+				Value: proptools.StringPtr(m.CrateName()),
+			},
+			Deps: protoDeps,
+		},
+	)
+}
diff --git a/rust/rust.go b/rust/rust.go
index 9494507..1ee99cd 100644
--- a/rust/rust.go
+++ b/rust/rust.go
@@ -1852,6 +1852,8 @@
 		procMacroBp2build(ctx, m)
 	} else if ctx.ModuleType() == "rust_binary_host" {
 		binaryBp2build(ctx, m)
+	} else if ctx.ModuleType() == "rust_protobuf_host" {
+		protoLibraryBp2build(ctx, m)
 	} else {
 		ctx.MarkBp2buildUnconvertible(bp2build_metrics_proto.UnconvertedReasonType_TYPE_UNSUPPORTED, "")
 	}