1
0
Fork 0
mirror of https://github.com/demostf/demo.js synced 2026-06-04 00:54:14 +02:00

Work around parsing errors for post MyM pov demos

This commit is contained in:
Robin Appelman 2016-12-22 00:02:24 +01:00
commit 265f87fe54
11 changed files with 37 additions and 24 deletions

View file

@ -89,7 +89,10 @@ export class Parser extends EventEmitter {
} }
} }
readMessage(stream, match): MessageParser|boolean { readMessage(stream:BitStream, match:Match): MessageParser|boolean {
if (stream.bitsLeft < 8) {
return false;
}
const type: MessageType = stream.readBits(8); const type: MessageType = stream.readBits(8);
if (type === MessageType.Stop) { if (type === MessageType.Stop) {
return false; return false;

View file

@ -97,7 +97,7 @@ export class DataTable extends Parser {
this.match.serverClasses.push(new ServerClass(classId, className, dataTable)); this.match.serverClasses.push(new ServerClass(classId, className, dataTable));
} }
const bitsLeft = (this.length * 8) - this.stream._index; const bitsLeft = (this.length * 8) - this.stream.index;
if (bitsLeft > 7 || bitsLeft < 0) { if (bitsLeft > 7 || bitsLeft < 0) {
throw "unexpected remaining data in datatable (" + bitsLeft + " bits)"; throw "unexpected remaining data in datatable (" + bitsLeft + " bits)";
} }

View file

@ -45,7 +45,7 @@ export class Packet extends Parser {
} }
get bitsLeft() { get bitsLeft() {
return (this.length * 8) - this.stream._index; return (this.length * 8) - this.stream.index;
} }
static parsers: PacketParserMap = { static parsers: PacketParserMap = {

View file

@ -1,5 +1,6 @@
import {Parser} from './Parser'; import {Parser} from './Parser';
import {StringTableEntry} from "../../Data/StringTable"; import {StringTableEntry} from "../../Data/StringTable";
import {RemoteInfo} from "dgram";
export class StringTable extends Parser { export class StringTable extends Parser {
parse() { parse() {
@ -23,8 +24,16 @@ export class StringTable extends Parser {
tables: tables tables: tables
}]; }];
} }
if (this.stream.readBits(1)) { if (this.stream.readBoolean()) {
extraDataLength = this.stream.readUint16(); extraDataLength = this.stream.readUint16();
if ((extraDataLength * 8) > this.stream.bitsLeft) {
// extradata to long, can't continue parsing the tables
// seems to happen in POV demos after the MyM update
return [{
packetType: 'stringTable',
tables: tables
}];
}
if (tableName === 'instancebaseline') { if (tableName === 'instancebaseline') {
this.match.staticBaseLines[parseInt(entry.text, 10)] = this.stream.readBitStream(8 * extraDataLength); this.match.staticBaseLines[parseInt(entry.text, 10)] = this.stream.readBitStream(8 * extraDataLength);
} else { } else {
@ -55,11 +64,11 @@ export class StringTable extends Parser {
} }
readExtraData(length):string[] { readExtraData(length):string[] {
const end = this.stream._index + (length * 8); const end = this.stream.index + (length * 8);
let data:string[] = []; let data:string[] = [];
//console.log(this.stream.readUTF8String()); //console.log(this.stream.readUTF8String());
data.push(this.stream.readUTF8String()); data.push(this.stream.readUTF8String());
while (this.stream._index < end) { while (this.stream.index < end && this.stream.index < (this.stream.length - 7)) { // -7 because we need a full byte
try { try {
let string = this.stream.readUTF8String(); let string = this.stream.readUTF8String();
if (string) { if (string) {
@ -69,7 +78,7 @@ export class StringTable extends Parser {
return data; return data;
} }
} }
this.stream._index = end; this.stream.index = end;
return data; return data;
} }
} }

View file

@ -49,10 +49,10 @@ const getGameEventValue = function (stream: BitStream, entry: GameEventEntry): G
export function GameEvent(stream: BitStream, match: Match): Packet { // 25: game event export function GameEvent(stream: BitStream, match: Match): Packet { // 25: game event
const length = stream.readBits(11); const length = stream.readBits(11);
const end = stream._index + length; const end = stream.index + length;
const eventId = stream.readBits(9); const eventId = stream.readBits(9);
const event = parseGameEvent(eventId, stream, match.eventDefinitions); const event = parseGameEvent(eventId, stream, match.eventDefinitions);
stream._index = end; stream.index = end;
return { return {
packetType: 'gameEvent', packetType: 'gameEvent',
event: event event: event

View file

@ -58,9 +58,9 @@ function readEnterPVS(stream: BitStream, entityId: number, match: Match, baseLin
} else { } else {
const staticBaseLine = match.staticBaseLines[serverClass.id]; const staticBaseLine = match.staticBaseLines[serverClass.id];
if (staticBaseLine) { if (staticBaseLine) {
const streamStart = staticBaseLine._index; const streamStart = staticBaseLine.index;
applyEntityUpdate(entity, staticBaseLine); applyEntityUpdate(entity, staticBaseLine);
staticBaseLine._index = streamStart; staticBaseLine.index = streamStart;
} }
} }
return entity; return entity;
@ -85,10 +85,10 @@ export function PacketEntities(stream: BitStream, match: Match): Packet { //26:
const updatedEntries = stream.readBits(11); const updatedEntries = stream.readBits(11);
const length = stream.readBits(20); const length = stream.readBits(20);
const updatedBaseLine = stream.readBoolean(); const updatedBaseLine = stream.readBoolean();
const end = stream._index + length; const end = stream.index + length;
let entityId = -1; let entityId = -1;
stream._index = end; stream.index = end;
return { return {
packetType: 'packetEntities' packetType: 'packetEntities'
}; };
@ -144,7 +144,7 @@ export function PacketEntities(stream: BitStream, match: Match): Packet { //26:
} }
} }
stream._index = end; stream.index = end;
return { return {
packetType: 'packetEntities' packetType: 'packetEntities'
}; };

View file

@ -4,7 +4,8 @@ import {Packet} from "../../Data/Packet";
export function PacketStringTable(stream: BitStream):Packet { export function PacketStringTable(stream: BitStream):Packet {
//todo //todo
// https://coldemoplayer.googlecode.com/svn/branches/2.0/code/plugins/CDP.Source/Messages/SvcCreateStringTable.cs // https://coldemoplayer.googlecode.com/svn/branches/2.0/code/plugins/CDP.Source/Messages/SvcCreateStringTable.cs
stream._index = stream._view._view.byteLength * 8; // throw new Error('packetstringtable not implemented');
stream.index = stream.length; // no idea, skip to the end of the
return { return {
packetType: 'stringTableTODO' packetType: 'stringTableTODO'
}; };

View file

@ -5,7 +5,7 @@ export function ParseSounds(stream: BitStream): Packet { // 17: parseSounds
const reliable = stream.readBoolean(); const reliable = stream.readBoolean();
const num = (reliable) ? 1 : stream.readUint8(); const num = (reliable) ? 1 : stream.readUint8();
const length = (reliable) ? stream.readUint8() : stream.readUint16(); const length = (reliable) ? stream.readUint8() : stream.readUint16();
stream._index += length; stream.index += length;
return { return {
packetType: 'parseSounds', packetType: 'parseSounds',
reliable: reliable, reliable: reliable,

View file

@ -7,7 +7,7 @@ import {applyEntityUpdate} from "../EntityDecoder";
export function TempEntities(stream: BitStream, match: Match): Packet { // 10: classInfo export function TempEntities(stream: BitStream, match: Match): Packet { // 10: classInfo
const entityCount = stream.readBits(8); const entityCount = stream.readBits(8);
const length = readVarInt(stream); const length = readVarInt(stream);
const end = stream._index + length; const end = stream.index + length;
// let entity: Entity|null = null; // let entity: Entity|null = null;
// let entities: Entity[] = []; // let entities: Entity[] = [];
@ -29,11 +29,11 @@ export function TempEntities(stream: BitStream, match: Match): Packet { // 10: c
// } // }
// console.log(entity); // console.log(entity);
// } // }
// if (end - stream._index > 8) { // if (end - stream.index > 8) {
// throw new Error("unexpected content after TempEntities"); // throw new Error("unexpected content after TempEntities");
// } // }
stream._index = end; stream.index = end;
return { return {
'packetType': 'tempEntities' 'packetType': 'tempEntities'
} }

View file

@ -72,7 +72,7 @@ const userMessageParsers = {
export function UserMessage(stream: BitStream): Packet { // 23: user message export function UserMessage(stream: BitStream): Packet { // 23: user message
const type = stream.readBits(8); const type = stream.readBits(8);
const length = stream.readBits(11); const length = stream.readBits(11);
const pos = stream._index; const pos = stream.index;
let result; let result;
if (userMessageParsers[type]) { if (userMessageParsers[type]) {
result = userMessageParsers[type](stream); result = userMessageParsers[type](stream);
@ -82,6 +82,6 @@ export function UserMessage(stream: BitStream): Packet { // 23: user message
type: type type: type
} }
} }
stream._index = pos + length; stream.index = pos + length;
return result; return result;
} }

View file

@ -4,14 +4,14 @@ import {BitStream} from 'bit-buffer';
export function SayText2(stream: BitStream): Packet { // 4: SayText2 export function SayText2(stream: BitStream): Packet { // 4: SayText2
var client = stream.readBits(8); var client = stream.readBits(8);
var raw = stream.readBits(8); var raw = stream.readBits(8);
var pos = stream._index; var pos = stream.index;
var from, text, kind, arg1, arg2; var from, text, kind, arg1, arg2;
if (stream.readBits(8) === 1) { if (stream.readBits(8) === 1) {
var first = stream.readBits(8); var first = stream.readBits(8);
if (first === 7) { if (first === 7) {
var color = stream.readUTF8String(6); var color = stream.readUTF8String(6);
} else { } else {
stream._index = pos + 8; stream.index = pos + 8;
} }
text = stream.readUTF8String(); text = stream.readUTF8String();
if (text.substr(0, 6) === '*DEAD*') { if (text.substr(0, 6) === '*DEAD*') {
@ -23,7 +23,7 @@ export function SayText2(stream: BitStream): Packet { // 4: SayText2
kind = 'TF_Chat_AllDead'; kind = 'TF_Chat_AllDead';
} }
} else { } else {
stream._index = pos; stream.index = pos;
kind = stream.readUTF8String(); kind = stream.readUTF8String();
from = stream.readUTF8String(); from = stream.readUTF8String();
text = stream.readUTF8String(); text = stream.readUTF8String();