Fix house data corruption, progress to first screen

This commit is contained in:
elasota
2019-12-24 18:39:30 -05:00
parent 3111609536
commit 5cb9b85396
30 changed files with 896 additions and 113 deletions

View File

@@ -72,13 +72,13 @@ void DrawBanner (Point *topLeft)
theErr = CreateOffScreenGWorld(&tempMask, &mapBounds, 1);
SetGWorld(tempMask, nil);
LoadGraphic(kBannerPageBottomMask);
CopyMask((BitMap *)*GetGWorldPixMap(tempMap),
(BitMap *)*GetGWorldPixMap(tempMask),
(BitMap *)*GetGWorldPixMap(workSrcMap),
&mapBounds, &mapBounds, &partPage);
SetPort((GrafPtr)workSrcMap);
SetGWorld(wasCPort, wasWorld);
DisposeGWorld(tempMap);
DisposeGWorld(tempMask);
@@ -176,6 +176,9 @@ void BringUpBanner (void)
DrawBanner(&topLeft);
DrawBannerMessage(topLeft);
DumpScreenOn(&justRoomsRect);
// if (quickerTransitions)
// DissBitsChunky(&justRoomsRect); // was workSrcRect
// else
@@ -186,6 +189,7 @@ void BringUpBanner (void)
CopyBits((BitMap *)*GetGWorldPixMap(backSrcMap),
(BitMap *)*GetGWorldPixMap(workSrcMap),
&wholePage, &wholePage, srcCopy, nil);
if (demoGoing)
WaitForInputEvent(4);

View File

@@ -474,6 +474,8 @@ void DoDiedGameOver (void)
pagesStuck = 8;
userAborted = true;
}
Delay(1, nullptr);
}
while (TickCount() < nextLoop);
nextLoop = TickCount() + 2;

View File

@@ -194,7 +194,11 @@ typedef struct
Boolean unusedBoolean; // 1
int16_t firstRoom; // 2
int16_t nRooms; // 2
int16_t padding;
roomType rooms[1]; // 348 * nRooms
static const size_t kBinaryDataSize = 866;
} houseType, *housePtr, **houseHand; // total = 866 +
typedef struct

View File

@@ -598,7 +598,7 @@ bool ByteSwapHouse(housePtr house, size_t sizeInBytes)
PortabilityLayer::ByteSwap::BigInt16(house->firstRoom);
PortabilityLayer::ByteSwap::BigInt16(house->nRooms);
const size_t roomDataSize = sizeInBytes + sizeof(roomType) - sizeof(houseType);
const size_t roomDataSize = sizeInBytes - houseType::kBinaryDataSize;
if (house->nRooms < 1 || roomDataSize / sizeof(roomType) < static_cast<size_t>(house->nRooms))
return false;
@@ -614,6 +614,9 @@ Boolean ReadHouse (void)
long byteCount;
OSErr theErr;
short whichRoom;
// There should be no padding remaining the house type
PL_STATIC_ASSERT(sizeof(houseType) - sizeof(roomType) == houseType::kBinaryDataSize + 2);
if (!houseOpen)
{
@@ -649,8 +652,11 @@ Boolean ReadHouse (void)
if (thisHouse != nil)
DisposeHandle((Handle)thisHouse);
// GP: Correct for padding
const size_t alignmentPadding = sizeof(houseType) - sizeof(roomType) - houseType::kBinaryDataSize;
thisHouse = (houseHand)NewHandle(byteCount);
thisHouse = (houseHand)NewHandle(byteCount + alignmentPadding);
if (thisHouse == nil)
{
YellowAlert(kYellowNoMemory, 10);
@@ -666,14 +672,24 @@ Boolean ReadHouse (void)
}
HLock((Handle)thisHouse);
theErr = FSRead(houseRefNum, &byteCount, *thisHouse);
if (theErr != noErr)
long readByteCount = byteCount;
theErr = FSRead(houseRefNum, &readByteCount, *thisHouse);
if (theErr != noErr || readByteCount != byteCount || byteCount < static_cast<long>(houseType::kBinaryDataSize))
{
CheckFileError(theErr, thisHouseName);
HUnlock((Handle)thisHouse);
return(false);
}
if (alignmentPadding != 0)
{
// GP: Correct for padding
const size_t roomDataSize = byteCount - houseType::kBinaryDataSize;
uint8_t *houseDataBytes = reinterpret_cast<uint8_t*>(*thisHouse);
memmove((*thisHouse)->rooms, houseDataBytes + houseType::kBinaryDataSize, roomDataSize);
}
ByteSwapHouse(*thisHouse, static_cast<size_t>(byteCount));
numberRooms = (*thisHouse)->nRooms;
@@ -791,14 +807,27 @@ Boolean WriteHouse (Boolean checkIt)
ByteSwapHouse(*thisHouse, static_cast<size_t>(byteCount));
theErr = FSWrite(houseRefNum, &byteCount, *thisHouse);
long headerSize = houseType::kBinaryDataSize;
long roomsSize = sizeof(roomType) * (*thisHouse)->nRooms;
theErr = FSWrite(houseRefNum, &headerSize, *thisHouse);
if (theErr != noErr)
{
CheckFileError(theErr, thisHouseName);
ByteSwapHouse(*thisHouse, static_cast<size_t>(byteCount));
HUnlock((Handle)thisHouse);
return(false);
}
theErr = FSWrite(houseRefNum, &roomsSize, (*thisHouse)->rooms);
if (theErr != noErr)
{
CheckFileError(theErr, thisHouseName);
ByteSwapHouse(*thisHouse, static_cast<size_t>(byteCount));
HUnlock((Handle)thisHouse);
return(false);
}
ByteSwapHouse(*thisHouse, static_cast<size_t>(byteCount));
theErr = SetEOF(houseRefNum, byteCount);

View File

@@ -74,7 +74,6 @@ extern Boolean switchedOut;
void NewGame (short mode)
{
Rect tempRect;
Size freeBytes, growBytes;
OSErr theErr;
Boolean wasPlayMusicPref;
@@ -192,8 +191,6 @@ void NewGame (short mode)
InitTelephone();
wasPlayMusicPref = isPlayMusicGame;
freeBytes = MaxMem(&growBytes);
#ifdef CREATEDEMODATA
SysBeep(1);
#endif

View File

@@ -616,14 +616,18 @@ void RenderShreds (void)
void CopyRectsQD (void)
{
short i;
CGrafPtr mainWindowGraf = GetWindowPort(mainWindow);
for (i = 0; i < numWork2Main; i++)
{
CopyBits((BitMap *)*GetGWorldPixMap(workSrcMap),
GetPortBitMapForCopyBits(GetWindowPort(mainWindow)),
GetPortBitMapForCopyBits(mainWindowGraf),
&work2MainRects[i], &work2MainRects[i],
srcCopy, nil);
}
mainWindowGraf->m_port.SetDirty(PortabilityLayer::QDPortDirtyFlag_Contents);
for (i = 0; i < numBack2Work; i++)
{
@@ -661,6 +665,7 @@ void RenderFrame (void)
while (TickCount() < nextFrame)
{
Delay(1, nullptr);
}
nextFrame = TickCount() + kTicksPerFrame;

View File

@@ -138,8 +138,12 @@ void WipeScreenOn (short direction, Rect *theRect)
void DumpScreenOn (Rect *theRect)
{
CGrafPtr graf = GetWindowPort(mainWindow);
CopyBits((BitMap *)*GetGWorldPixMap(workSrcMap),
GetPortBitMapForCopyBits(GetWindowPort(mainWindow)),
GetPortBitMapForCopyBits(graf),
theRect, theRect, srcCopy, nil);
graf->m_port.SetDirty(PortabilityLayer::QDPortDirtyFlag_Contents);
}

View File

@@ -248,8 +248,9 @@ OSErr CreateOffScreenGWorld (GWorldPtr *theGWorld, Rect *bounds, short depth)
if (theErr)
theErr = NewGWorld(theGWorld, depth, bounds, nil, nil, 0);
LockPixels(GetGWorldPixMap(*theGWorld));
if (!theErr)
LockPixels(GetGWorldPixMap(*theGWorld));
return theErr;
}
@@ -450,6 +451,8 @@ Boolean WaitForInputEvent (short seconds)
}
if ((seconds != -1) && (TickCount() >= timeToBail))
waiting = false;
Delay(1, nullptr);
}
FlushEvents(everyEvent, 0);
return (didResume);