This CL fixes an unnecessary string copy. `Message::GetTypeName()` always
returns a copy, but we can avoid this by relying on `Descriptor::full_name()`
instead.
PiperOrigin-RevId: 675237607
Everything should work without this change, because all references are done to a single definition. But the accidental duplication needs to be removed eventually.
PiperOrigin-RevId: 675211197
The change is no-op for Bazel < 8, it always falls back to native providers.
When we cherry-pick --incompatible_autoload_externally to older Bazels, ProtoInfo
can be replaced with Starlark implementation, providing that users set the flag so that there is no second implementation exposed from Bazel.
PiperOrigin-RevId: 674561141
This CL doesn't unbreak the bazel tests, but is yak shaving in prep for changes that will. This makes it more straightforward how the tests are broken by having bazel test rules name rust proto library targets that don't exist in bazel repo, instead of naming targets that do exist but are bogus.
Also correct unittest_edition target to match the order of words in the .proto file name (edition_unittest)
PiperOrigin-RevId: 674295376
The logic to create new elements in `RepeatedPtrField` was spread across an assorted collection of specializations of `GenericTypeHandler`, individual `GenericTypeHandler` static functions, and external member and non-member functions, all living in multiple sources. Now all that logic is concentrated in three symmetric `GenericTypeHandler` specializations.
PiperOrigin-RevId: 674064544
Bazel 6 falls back to native rules, because of ProtoInfo differences.
Bazel 7 is slightly degraded: Kythe flags don't work, DebugContext is left out from CcInfo and temporary files generated by the C++ compiler (but it's only useful for debugging).
Tests will be submitted in separate PRs.
PiperOrigin-RevId: 674030212
I realized that as long as we implement `UpbTypeConversions` for enums, we can
easily get the blanket implementation for messages to work for enums as well.
Luckily the blanket implementation also happens to work for non-generated
types, so this gets us down to just one ProxiedInMapValue implementation for
upb.
PiperOrigin-RevId: 673927343
This avoids allocating a backing array of size 10 when we are adding >10 elements.
- If we are adding objects one at a time, inflate a Object[10] and continue.
- If we are adding objects from a Collection, assume this is the only collection we are adding, and inflate a `Object[collection.size()]`
- If the existing array is non-empty, resize the array by 1.5x exponential growth as usual.
There's another small change where if we're addAll(<10 elements), we allocate an exact-sized backing array (e.g. size=3), rather than rounding up to size 10. See android/LiteAllocationTest. I think this is good: this will save memory in the common case of just calling .addAll() once, and if we call addAll twice, we grow still exponentially. But we could decide to avoid this or split it out into its own change.
This change involves moving some logic out of GeneratedMessageLite. I think the default size of the backing array is better handled inside ProtobufArrayList than inside GeneratedMessageLite's wrapper function.
PiperOrigin-RevId: 673612155
But check that the given byte size is within the bounds of the byte[] first, otherwise we might get OutOfMemoryErrors on bitflipped input that tries to allocate huge arrays.
Add some tests that would have otherwise OutOfMemoryError'd in order to have some confidence that we won't OOM.
PiperOrigin-RevId: 673597245
I'm just about to edit this code, and I want these tests for my peace of mind.
Also update the other callers to use assertThrows for consistency.
PiperOrigin-RevId: 673590917
This has twofold goals:
1. Correctness: if position overruns the array, checking space left may return a negative number. I'm not sure how bad that is, but let's avoid it.
2. Performance. This generates more optimal assembly code which can combine bounds checks, particularly on Android (I haven't looked at the generated assembly on the server JVM; it's possible the server JVM can already performance this hoist).
The `position` field is stored on the object, so Android ART generates assembly codes for `this.position++` like "load, add, store":
```
ldr w3, [x1, #12]
add w4, w3, #0x1 (1)
str w4, [x1, #12]
```
There can be a lot of these loads/stores executed each step of a loop (e.g. writeFixed64NoTag updates position 8 times, and varint encoding could do it even more). It's faster if we can hoist these so we load once at the start of the function, and store once at the end of the function. This also has the nice benefit that it won't store if we've thrown an exception.
See before/after in Compiler Explorer: https://godbolt.org/z/bWWYqsxK4. I'm not an assembly expert, but it seems clear that the increment instructions like `add w4, w0, #0x1 (1)` are no longer always surrounded by loads and stores in the new version.
And in Compiler Explorer, you also see `bufferFixed64NoTag` has reduced from 98 lines of assembly to 57 lines of assembly in the hoisted version. This is because we don't need to re-check the array bounds each time we reload `position`. I imagine this also makes any other method with a fixed number of increments like `writeFixed32NoTag` faster too.
PiperOrigin-RevId: 673588324