Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added new SDL descriptor syntax STATEDIFF #147

Closed
wants to merge 1 commit into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Sources/Plasma/PubUtilLib/plSDL/plSDL.h
Original file line number Diff line number Diff line change
Expand Up @@ -514,6 +514,7 @@ class plSDLParser
bool IParseVarDesc(const char* fileName, hsStream* stream, char token[], plStateDescriptor*& curDesc,
plVarDescriptor*& curVar) const;
bool IParseStateDesc(const char* fileName, hsStream* stream, char token[], plStateDescriptor*& curDesc) const;
bool IParseStateDiff(const char* fileName, hsStream* stream, char token[], plStateDescriptor*& curDesc) const;

void DebugMsg(const char* fmt, ...) const;
void DebugMsgV(const char* fmt, va_list args) const;
Expand Down
1 change: 1 addition & 0 deletions Sources/Plasma/PubUtilLib/plSDL/plSDLDescriptor.h
Original file line number Diff line number Diff line change
Expand Up @@ -244,6 +244,7 @@ class plStateDescriptor
void SetVersion(int v) { fVersion=v; }
void SetName(const char* n) { delete [] fName; fName=hsStrcpy(n); }
void AddVar(plVarDescriptor* v) { fVarsList.push_back(v); }
void DelVar( const char * n );
void SetFilename( const char * n ) { fFilename=n;}

plVarDescriptor* FindVar(const char* name, int* idx=nil) const;
Expand Down
154 changes: 143 additions & 11 deletions Sources/Plasma/PubUtilLib/plSDL/plSDLParser.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -154,6 +154,80 @@ bool plSDLParser::IParseStateDesc(const char* fileName, hsStream* stream, char t
return false;
}

//
// Parse a state diff
// Find the original desc and copy it
// set new version
//
bool plSDLParser::IParseStateDiff(const char* fileName, hsStream* stream, char token[], plStateDescriptor*& curDesc) const
{
plSDL::DescriptorList* descList = &plSDLMgr::GetInstance()->fDescriptors;

bool ok = true;

char* name = token;
DebugMsg("SDL: DIFF name=%s", token);

//
// {
//
stream->GetToken(token, kTokenLen); // skip '{'

//
// VERSION
//
if (stream->GetToken(token, kTokenLen))
{
if (!strcmp(token, "VERSION"))
{
// read desc version
if (stream->GetToken(token, kTokenLen))
{
int v = atoi(token);
plStateDescriptor* prevDesc = plSDLMgr::GetInstance()->FindDescriptor(token, v - 1);
hsAssert(prevDesc, xtl::format("Could not find previous version of %s (%d), fileName=%s", name, v - 1, fileName).c_str());
curDesc = new plStateDescriptor(*prevDesc);
curDesc->SetVersion(v);
DebugMsg("\tVersion=%d", v);
}
}
else
{
hsAssert(false, xtl::format("Error parsing state diff, missing VERSION, fileName=%s",
fileName).c_str());
ok = false;
}
}
else
{
hsAssert(false, xtl::format("Error parsing state diff, fileName=%s", fileName).c_str());
ok = false;
}

if ( ok )
{
ok = ( plSDLMgr::GetInstance()->FindDescriptor(curDesc->GetName(), curDesc->GetVersion())==nil );
if ( !ok )
{
std::string err = xtl::format( "Found duplicate SDL descriptor for %s version %d.\nFailed to parse file: %s", curDesc->GetName(), curDesc->GetVersion(), fileName );
plNetApp::StaticErrorMsg( err.c_str() );
hsAssert( false, err.c_str() );
}
}

if ( ok )
{
descList->push_back(curDesc);
}
else
{
delete curDesc;
curDesc = nil;
}

return false;
}

//
// Parse a variable descriptor.
// read type, name, count [default]
Expand Down Expand Up @@ -334,9 +408,10 @@ bool plSDLParser::ILoadSDLFile(const char* fileName) const
plVarDescriptor* curVar=nil;
plStateDescriptor* curDesc=nil;
char token[kTokenLen];
bool parsingStateDesc=false;
enum parsingStates { kRoot, kDesc, kDiff, kVar, kAdd, kRemove, kUpdate, kDone };
parsingStates parsingState=kRoot;
bool skip=false;
while (1)
while (parsingState != kDone)
{
if (!skip)
{
Expand All @@ -347,14 +422,43 @@ bool plSDLParser::ILoadSDLFile(const char* fileName) const

if (!strcmp(token, "VAR"))
{
parsingStateDesc=false;
hsAssert(parsingState == kDiff, xtl::format("VAR outside of STATEDESC block in %s", fileName).cstr());
parsingState=kVar;
curVar=nil; // start fresh
continue;
}

if (!strcmp(token, "ADD"))
{
hsAssert(parsingState == kDiff, xtl::format("ADD outside of STATEDIFF block in %s", fileName).cstr());
parsingState=kAdd;
continue;
}

if (!strcmp(token, "REMOVE"))
{
hsAssert(parsingState == kDiff, xtl::format("REMOVE outside of STATEDIFF block in %s", fileName).cstr());
parsingState=kRemove;
continue;
}

if (!strcmp(token, "UPDATE"))
{
hsAssert(parsingState == kDiff, xtl::format("UPDATE outside of STATEDIFF block in %s", fileName).cstr());
parsingState=kUpdate;
continue;
}

if (!strcmp(token, "STATEDESC"))
{
parsingStateDesc=true;
parsingState=kDesc;
curDesc=nil; // start fresh
continue;
}

if (!strcmp(token, "STATEDIFF"))
{
parsingState=kDiff;
curDesc=nil; // start fresh
continue;
}
Expand All @@ -363,19 +467,47 @@ bool plSDLParser::ILoadSDLFile(const char* fileName) const
{
if ( curDesc )
curDesc->SetFilename( fileName );
parsingStateDesc=false;
continue;
parsingState=kRoot;
}

if (parsingStateDesc)
switch(parsingState)
{
case kDesc:
skip=IParseStateDesc(fileName, stream, token, curDesc);
if ( !curDesc )
break; // failed to parse state desc
}
else
{
parsingState=kDone; // failed to parse state desc
break;
case kDiff:
// finds the previous version of the named STATEDESC, copies into curDesc
skip=IParseStateDiff(fileName, stream, token, curDesc);
if( !curDesc )
parsingState=kDone; // failed to parse state diff
break;
case kRemove:
// the current token is the name of the var we need to remove
curDesc->DelVar(token);
break;
case kUpdate:
// removes and re-adds the named variable
// we look ahead past the type to get the var name, and remove it
// the fall through to ADD
{
char* nextToken = token;
stream->GetToken(nextToken, kTokenLen);
curDesc->DelVar(nextToken);
}
case kAdd:
// same as normal var desc but we return to the diff state
skip=IParseVarDesc(fileName, stream, token, curDesc, curVar);
parsingState=kDiff;
break;
case kVar:
skip=IParseVarDesc(fileName, stream, token, curDesc, curVar);
parsingState=kDesc;
break;
default:
hsAssert(false, "Invalid state in SDL parser");
break;
}
}

Expand Down
11 changes: 11 additions & 0 deletions Sources/Plasma/PubUtilLib/plSDL/plStateDescriptor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,17 @@ void plStateDescriptor::IDeInit()
fVarsList.clear();
}

void plStateDescriptor::DelVar(const char* n) {
for(VarsList::iterator it = fVarsList.begin(); it != fVarsList.end(); it++)
{
if(!stricmp((*it)->GetName(), n))
{
fVarsList.erase(it);
break;
}
}
}

plVarDescriptor* plStateDescriptor::FindVar(const char* name, int* idx) const
{
VarsList::const_iterator it;
Expand Down