mirror of
https://github.com/microsoft/Microsoft-3D-Movie-Maker.git
synced 2024-11-22 02:12:33 +01:00
462 lines
11 KiB
C++
462 lines
11 KiB
C++
/* Copyright (c) Microsoft Corporation.
|
|
Licensed under the MIT License. */
|
|
|
|
/***************************************************************************
|
|
Author: ******
|
|
Project: Kauai
|
|
Reviewed:
|
|
Copyright (c) Microsoft Corporation
|
|
|
|
Chunky source emitter class implementation.
|
|
|
|
***************************************************************************/
|
|
#include "util.h"
|
|
ASSERTNAME
|
|
|
|
RTCLASS(CHSE)
|
|
|
|
|
|
/***************************************************************************
|
|
Constructor for a chunky source emitter.
|
|
***************************************************************************/
|
|
CHSE::CHSE(void)
|
|
{
|
|
AssertBaseThis(0);
|
|
_pmsnkError = pvNil;
|
|
_pmsnkDump = pvNil;
|
|
AssertThis(0);
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Destructor for a chunky source emitter.
|
|
***************************************************************************/
|
|
CHSE::~CHSE(void)
|
|
{
|
|
Uninit();
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Initialize the chunky source emitter.
|
|
***************************************************************************/
|
|
void CHSE::Init(PMSNK pmsnkDump, PMSNK pmsnkError)
|
|
{
|
|
AssertThis(0);
|
|
AssertPo(pmsnkDump, 0);
|
|
AssertNilOrPo(pmsnkError, 0);
|
|
|
|
Uninit();
|
|
|
|
_pmsnkDump = pmsnkDump;
|
|
_pmsnkDump->AddRef();
|
|
_pmsnkError = pmsnkError;
|
|
if (_pmsnkError != pvNil)
|
|
_pmsnkError->AddRef();
|
|
|
|
AssertThis(fchseDump);
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Clean up and return the chse to an inactive state.
|
|
***************************************************************************/
|
|
void CHSE::Uninit(void)
|
|
{
|
|
AssertThis(0);
|
|
ReleasePpo(&_pmsnkDump);
|
|
ReleasePpo(&_pmsnkError);
|
|
if (_bsf.IbMac() > 0)
|
|
_bsf.FReplace(pvNil, 0, 0, _bsf.IbMac());
|
|
}
|
|
|
|
|
|
#ifdef DEBUG
|
|
/***************************************************************************
|
|
Assert the validity of a CHSE.
|
|
***************************************************************************/
|
|
void CHSE::AssertValid(ulong grfchse)
|
|
{
|
|
CHSE_PAR::AssertValid(0);
|
|
AssertPo(&_bsf, 0);
|
|
if (grfchse & fchseDump)
|
|
AssertPo(_pmsnkDump, 0);
|
|
AssertNilOrPo(_pmsnkError, 0);
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Mark memory for the CHSE.
|
|
***************************************************************************/
|
|
void CHSE::MarkMem(void)
|
|
{
|
|
AssertValid(0);
|
|
CHSE_PAR::MarkMem();
|
|
MarkMemObj(_pmsnkError);
|
|
MarkMemObj(_pmsnkDump);
|
|
MarkMemObj(&_bsf);
|
|
}
|
|
#endif //DEBUG
|
|
|
|
|
|
/***************************************************************************
|
|
Dumps chunk header.
|
|
***************************************************************************/
|
|
void CHSE::DumpHeader(CTG ctg, CNO cno, PSTN pstnName, bool fPack)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertNilOrPo(pstnName, 0);
|
|
|
|
STN stnT;
|
|
|
|
if (pstnName != pvNil)
|
|
{
|
|
STN stnName;
|
|
|
|
stnName = *pstnName;
|
|
stnName.FExpandControls();
|
|
stnT.FFormatSz(PszLit("CHUNK('%f', %d, \"%s\")"), ctg, cno, &stnName);
|
|
}
|
|
else
|
|
stnT.FFormatSz(PszLit("CHUNK('%f', %d)"), ctg, cno);
|
|
|
|
DumpSz(stnT.Psz());
|
|
if (fPack)
|
|
DumpSz(PszLit("\tPACK"));
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Dump a raw data chunk
|
|
***************************************************************************/
|
|
void CHSE::DumpBlck(PBLCK pblck)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertPo(pblck, 0);
|
|
|
|
FLO flo;
|
|
|
|
if (pblck->FPacked())
|
|
DumpSz(PszLit("PREPACKED"));
|
|
if (!pblck->FGetFlo(&flo, fTrue))
|
|
{
|
|
Error(PszLit("Dumping chunk failed"));
|
|
return;
|
|
}
|
|
_bsf.FReplaceFlo(&flo, fFalse, 0, _bsf.IbMac());
|
|
ReleasePpo(&flo.pfil);
|
|
_DumpBsf(1);
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Dump raw data from memory.
|
|
***************************************************************************/
|
|
void CHSE::DumpRgb(void *prgb, long cb, long cactTab)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertIn(cb, 0, kcbMax);
|
|
AssertPvCb(prgb, cb);
|
|
|
|
if (cb > 0)
|
|
{
|
|
_bsf.FReplace(prgb, cb, 0, _bsf.IbMac());
|
|
_DumpBsf(cactTab);
|
|
}
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Dump a parent directive
|
|
***************************************************************************/
|
|
void CHSE::DumpParentCmd(CTG ctgPar, CNO cnoPar, CHID chid)
|
|
{
|
|
AssertThis(fchseDump);
|
|
|
|
STN stn;
|
|
|
|
stn.FFormatSz(PszLit("PARENT('%f', %d, %d)"), ctgPar, cnoPar, chid);
|
|
DumpSz(stn.Psz());
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Dump a bitmap directive
|
|
***************************************************************************/
|
|
void CHSE::DumpBitmapCmd(byte bTransparent, long dxp, long dyp, PSTN pstnFile)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertPo(pstnFile, 0);
|
|
|
|
STN stn;
|
|
|
|
stn.FFormatSz(PszLit("BITMAP(%d, %d, %d) \"%s\""), (long)bTransparent, dxp,
|
|
dyp, pstnFile);
|
|
DumpSz(stn.Psz());
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Dump a file directive
|
|
***************************************************************************/
|
|
void CHSE::DumpFileCmd(PSTN pstnFile, bool fPacked)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertPo(pstnFile, 0);
|
|
|
|
STN stn;
|
|
|
|
if (fPacked)
|
|
stn.FFormatSz(PszLit("PACKEDFILE \"%s\""), pstnFile);
|
|
else
|
|
stn.FFormatSz(PszLit("FILE \"%s\""), pstnFile);
|
|
DumpSz(stn.Psz());
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Dump an adopt directive
|
|
***************************************************************************/
|
|
void CHSE::DumpAdoptCmd(CKI *pcki, KID *pkid)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertVarMem(pcki);
|
|
AssertVarMem(pkid);
|
|
|
|
STN stn;
|
|
|
|
stn.FFormatSz(PszLit("ADOPT('%f', %d, '%f', %d, %d)"),
|
|
pcki->ctg, pcki->cno, pkid->cki.ctg, pkid->cki.cno, pkid->chid);
|
|
DumpSz(stn.Psz());
|
|
}
|
|
|
|
|
|
/***************************************************************************
|
|
Dump the data in the _bsf
|
|
***************************************************************************/
|
|
void CHSE::_DumpBsf(long cactTab)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertIn(cactTab, 0, kcchMaxStn + 1);
|
|
|
|
byte rgb[8], bT;
|
|
STN stn1;
|
|
STN stn2;
|
|
long cact;
|
|
long ib, ibMac;
|
|
long cb, ibT;
|
|
|
|
stn1.SetNil();
|
|
for (cact = cactTab; cact-- > 0; )
|
|
stn1.FAppendCh(kchTab);
|
|
stn1.FAppendSz(PszLit("BYTE"));
|
|
DumpSz(stn1.Psz());
|
|
|
|
ibMac = _bsf.IbMac();
|
|
for (ib = 0; ib < ibMac; )
|
|
{
|
|
stn1.SetNil();
|
|
for (cact = cactTab; cact-- > 0; )
|
|
stn1.FAppendCh(kchTab);
|
|
|
|
cb = LwMin(ibMac - ib, size(rgb));
|
|
_bsf.FetchRgb(ib, cb, rgb);
|
|
|
|
//append the hex
|
|
for (ibT = 0; ibT < size(rgb); ibT++)
|
|
{
|
|
if (ibT >= cb)
|
|
stn1.FAppendSz(PszLit(" "));
|
|
else
|
|
{
|
|
stn2.FFormatSz(PszLit("0x%02x "), rgb[ibT]);
|
|
stn1.FAppendStn(&stn2);
|
|
}
|
|
}
|
|
stn1.FAppendSz(PszLit(" // '"));
|
|
|
|
//append the ascii
|
|
for (ibT = 0; ibT < cb; ibT++)
|
|
{
|
|
bT = rgb[ibT];
|
|
if (bT < 0x20 || bT == 0x7F)
|
|
bT = '?';
|
|
stn1.FAppendCh((achar)bT);
|
|
}
|
|
stn1.FAppendSz(PszLit("' "));
|
|
|
|
DumpSz(stn1.Psz());
|
|
ib += cb;
|
|
}
|
|
}
|
|
|
|
|
|
/******************************************************************************
|
|
Disassembles a script (pscpt) using the given script compiler (psccb)
|
|
and dumps the result (including a "SCRIPTPF" directive).
|
|
******************************************************************************/
|
|
bool CHSE::FDumpScript(PSCPT pscpt, PSCCB psccb)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertPo(pscpt, 0);
|
|
AssertPo(psccb, 0);
|
|
|
|
DumpSz(PszLit("SCRIPTPF"));
|
|
if (!psccb->FDisassemble(pscpt, _pmsnkDump, _pmsnkError))
|
|
{
|
|
Error(PszLit("Dumping script failed"));
|
|
return fFalse;
|
|
}
|
|
return fTrue;
|
|
}
|
|
|
|
|
|
/******************************************************************************
|
|
Dumps a GL or AL, including the GL or AL directive. pglb is the GL or AL
|
|
to dump.
|
|
******************************************************************************/
|
|
void CHSE::DumpList(PGLB pglb)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertPo(pglb, 0);
|
|
|
|
long cbEntry;
|
|
long iv, ivMac;
|
|
STN stn;
|
|
bool fAl = pglb->FIs(kclsAL);
|
|
|
|
Assert(fAl || pglb->FIs(kclsGL), "neither a GL or AL!");
|
|
|
|
// have a valid GL or AL -- print it out in readable format
|
|
cbEntry = pglb->CbEntry();
|
|
AssertIn(cbEntry, 0, kcbMax);
|
|
ivMac = pglb->IvMac();
|
|
|
|
stn.FFormatSz(fAl ? PszLit("\tAL(%d)") : PszLit("\tGL(%d)"), cbEntry);
|
|
DumpSz(stn.Psz());
|
|
|
|
// print out the entries
|
|
for (iv = 0; iv < ivMac; iv++)
|
|
{
|
|
if (pglb->FFree(iv))
|
|
DumpSz(PszLit("\tFREE"));
|
|
else
|
|
{
|
|
DumpSz(PszLit("\tITEM"));
|
|
_bsf.FReplace(pglb->PvLock(iv), cbEntry, 0, _bsf.IbMac());
|
|
pglb->Unlock();
|
|
_DumpBsf(2);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
/******************************************************************************
|
|
Dumps a GG or AG, including the GG or AG directive. pggb is the GG or AG
|
|
to dump.
|
|
******************************************************************************/
|
|
void CHSE::DumpGroup(PGGB pggb)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertPo(pggb, 0);
|
|
|
|
long cbFixed, cb;
|
|
long iv, ivMac;
|
|
STN stnT;
|
|
bool fAg = pggb->FIs(kclsAG);
|
|
|
|
Assert(fAg || pggb->FIs(kclsGG), "neither a GG or AG!");
|
|
|
|
// have a valid GG or AG -- print it out in readable format
|
|
cbFixed = pggb->CbFixed();
|
|
AssertIn(cbFixed, 0, kcbMax);
|
|
ivMac = pggb->IvMac();
|
|
|
|
stnT.FFormatSz(fAg ? PszLit("\tAG(%d)") : PszLit("\tGG(%d)"), cbFixed);
|
|
DumpSz(stnT.Psz());
|
|
|
|
// print out the entries
|
|
for (iv = 0; iv < ivMac; iv++)
|
|
{
|
|
if (pggb->FFree(iv))
|
|
{
|
|
DumpSz(PszLit("\tFREE"));
|
|
continue;
|
|
}
|
|
DumpSz(PszLit("\tITEM"));
|
|
if (cbFixed > 0)
|
|
{
|
|
_bsf.FReplace(pggb->PvFixedLock(iv), cbFixed, 0, _bsf.IbMac());
|
|
pggb->Unlock();
|
|
_DumpBsf(2);
|
|
}
|
|
if (0 < (cb = pggb->Cb(iv)))
|
|
{
|
|
DumpSz(PszLit("\tVAR"));
|
|
_bsf.FReplace(pggb->PvLock(iv), cb, 0, _bsf.IbMac());
|
|
pggb->Unlock();
|
|
_DumpBsf(2);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
/******************************************************************************
|
|
Dumps a GST or AST, including the GST or AST directive. pggb is the GST or
|
|
AST to dump.
|
|
******************************************************************************/
|
|
bool CHSE::FDumpStringTable(PGSTB pgstb)
|
|
{
|
|
AssertThis(fchseDump);
|
|
AssertPo(pgstb, 0);
|
|
|
|
long cbExtra;
|
|
long iv, ivMac;
|
|
STN stn1;
|
|
STN stn2;
|
|
void *pvExtra = pvNil;
|
|
bool fAst = pgstb->FIs(kclsAST);
|
|
|
|
Assert(fAst || pgstb->FIs(kclsGST), "neither a GST or AST!");
|
|
|
|
// have a valid GST or AST -- print it out in readable format
|
|
cbExtra = pgstb->CbExtra();
|
|
AssertIn(cbExtra, 0, kcbMax);
|
|
ivMac = pgstb->IvMac();
|
|
|
|
if (cbExtra > 0 && !FAllocPv(&pvExtra, cbExtra, fmemNil, mprNormal))
|
|
return fFalse;
|
|
|
|
stn1.FFormatSz(fAst ? PszLit("\tAST(%d)") : PszLit("\tGST(%d)"),
|
|
cbExtra);
|
|
DumpSz(stn1.Psz());
|
|
|
|
// print out the entries
|
|
for (iv = 0; iv < ivMac; iv++)
|
|
{
|
|
if (pgstb->FFree(iv))
|
|
{
|
|
DumpSz(PszLit("\tFREE"));
|
|
continue;
|
|
}
|
|
DumpSz(PszLit("\tITEM"));
|
|
|
|
pgstb->GetStn(iv, &stn2);
|
|
stn2.FExpandControls();
|
|
stn1.FFormatSz(PszLit("\t\t\"%s\""), &stn2);
|
|
DumpSz(stn1.Psz());
|
|
|
|
if (cbExtra > 0)
|
|
{
|
|
pgstb->GetExtra(iv, pvExtra);
|
|
_bsf.FReplace(pvExtra, cbExtra, 0, _bsf.IbMac());
|
|
_DumpBsf(2);
|
|
}
|
|
}
|
|
|
|
FreePpv(&pvExtra);
|
|
return fTrue;
|
|
}
|
|
|
|
|