Go Get
go get -u github.com/markus-wa/demoinfocs-golang/v6/pkg/demoinfocs@v6.0.0-rc.2
To upgrade from v5, this may be useful to update import paths (use at your own risk):
sed -i 's/demoinfocs-golang\/v5/demoinfocs-golang\/v6/' **/*.go
Coming from v5? Read the v6.0.0-rc.0 release notes. They list every change since v5.2.0 and include a migration table. This release only adds the changes below.
Demos recorded since the CS2 update of 2026-11-11 can't be parsed with rc.1 or earlier. This release fixes that.
Fixes
- Fix parsing of demos recorded since the CS2 update of 2026-11-11 by @pablosanches in #764 and @markus-wa in #765 (#763)
- The update added
uint8fields with thefixed8encoder toCCSPlayerController(m_recentKillQueue,m_nFirstKill,m_nKillCount). They were read as varints, so any value >= 128 consumed an extra byte and desynced the rest of the packet. Parsing failed withErrDecodeFailed(nextByte: insufficient buffer,variable collection size ... out of range). On v5 the process ran out of memory instead - Fields with a
fixed8/fixed16/fixed32encoder are now read as N raw bits - Their values keep the Go type that the base type's varint decoder returns (
int32sign-extended,uint64oruint32), so getters likePlayer.RankType()andPropertyValue.Int()/UInt32()work the same as before the update - Demos recorded before the update have no
fixedNfields, so their output doesn't change - Backports: v5 in #767. The v4
csdabranch, which cs-demo-analyzer uses, has the fix since decf1a6, and cs-demo-analyzer v1.14.1 includes it
- The update added
Performance
- A held
*sendtables.Propertyreads its value without hashing by @billfreeman44 in #762Propertykeeps the field path it resolved and re-resolves only after the entity's polymorphic types change (type switch or PVS re-entry). Before, eachValue()call looked the name up in a map- Reading a held
*Property: ~9 → ~2 ns. Reading by name withEntity.PropertyValue(name): ~16 → ~10 ns. No API change Value()now writes the resolved path on its first read. If you read the samePropertyfrom several goroutines after parsing, synchronize those reads yourself
UserCmdParsingFullreconstructs user commands with generated typed code instead of protobuf reflection by @billfreeman44 in #761- The baseline copy and the delta merge no longer clone and walk the protobuf messages reflectively.
s2_usercmd_typed.go, generated from themsgtypes byinternal/usercmdgen(and regenerated with the protos by the "Update Protobufs" workflow), does it with typed code. No public API change,go.moduntouched - Decoding one delta command (copy + merge): ~2,540–2,669 → ~1,197–1,416 ns/op, 69 → 26 allocs. The merge alone: ~1,286–1,329 → ~183–190 ns/op, 0 allocs
- csgo-rushb (every channel,
UserCmdParsingFull): 12.63 → 10.33 s (−18%) on a 212 MB demo, 30.70 → 21.71 s (−29%) on 431 MB, 1.94 → 1.59 s (−18%) on 31 MB - Together with the
Propertychange above, the sum of each demo's fastest of 3 parses over 10 production demos (30–412 MB) went from 140.8 to 99.5 s (−29%), with byte-identical output
- The baseline copy and the delta merge no longer clone and walk the protobuf messages reflectively.
Changes
- Internal, no API change:
sendtablesfield-path resolution was tidied up in #766. #770 adds a test that fails when the usercmd generator would silently drop a wire field, documents the accepted protobuf subset, and reports a generator gap as an issue instead of a silent red X
New Contributors
- @pablosanches made their first contribution in #764
Full Changelog: v6.0.0-rc.1...v6.0.0-rc.2