///|
fn read_update_fields(
reader : UpdateReader,
) -> (Array[RawItem], IdSet, Bool) raise DecodeError {
fn id(column : Int32) -> Id raise DecodeError {
{ client: reader.field(1), clock: codec_clock(reader.field(column)), }
}
fn length_count() -> Int32 raise DecodeError {
let n = codec_clock(reader.field(8))
guard n.to_uint64() <= reader.budget.to_uint64() else {
raise InvalidData("update exceeds decode item budget")
}
reader.budget -= n.reinterpret_as_int()
n.reinterpret_as_int()
}
let items = []
let clients = reader.count()
for _ in 0.. Some(Root(reader.string()))
0UL => Some(Nested(id(2)))
_ => raise InvalidData("invalid parent discriminator")
}
} else {
None
}
let parent_sub = if parent is Some(_) && (info & 32) != 0 {
Some(reader.string())
} else {
None
}
// Deleted runs carry no per-clock payload. Keep each internal block within
// signed indexing bounds while accepting the full unsigned wire range.
if kind == 0 || kind == 1 {
let length = codec_clock(reader.field(8))
guard clock.to_uint64() + length.to_uint64() <= 0xffff_ffffUL else {
raise InvalidData("clock overflow")
}
let end = clock + length
let mut left = origin
while clock < end {
let count = (end - clock).min(0x7fff_ffffU)
items.push({
id: { client, clock, },
origin: if kind == 0 {
None
} else {
left
},
right_origin,
parent,
parent_sub,
content: if kind == 0 {
Garbage(count.reinterpret_as_int())
} else {
Deleted(count.reinterpret_as_int())
},
})
clock += count
left = Some({ client, clock: clock - 1U, })
}
continue
}
let content = match kind {
2 => {
let values = []
let count = length_count()
for _ in 0.. raise InvalidData("invalid legacy JSON")
},
)
},
)
}
LegacyJson(ReadOnlyArray::from_array(values[:]))
}
9 => Subdocument(decode_subdocument(reader.string(), reader.raw.any()))
5 => Embed(reader.json())
6 => Format(reader.key(), reader.json())
7 =>
Shared(
match codec_byte(reader.field(7)).to_int() {
0 => SharedArray
1 => SharedMap
2 => SharedText
3 => SharedXmlElement(reader.key())
4 => SharedXmlFragment
6 => SharedXmlText
7 => SharedWeak(LinkSource::read(reader))
5 | 9 | 15 as reference => SharedOpaque(reference)
_ => raise InvalidData("unsupported shared type")
},
)
3 => Binary(reader.raw.buffer())
8 => {
let values = []
let count = length_count()
for _ in 0.. Characters(reader.string())
_ => raise InvalidData("unsupported item content")
}
let length = content.length()
guard clock.to_uint64() + length.to_uint64() <= 0xffff_ffffUL else {
raise InvalidData("clock overflow")
}
if length > 0 && kind != 10 {
items.push({
id: { client, clock, },
origin,
right_origin,
parent,
parent_sub,
content,
})
}
clock += length.reinterpret_as_uint()
}
}
let deletion_ranges = []
for _ in 0.. 0)
}