diff --git a/src/common/scripting/backend/codegen.cpp b/src/common/scripting/backend/codegen.cpp index b14fb267cd..df1c48c22e 100644 --- a/src/common/scripting/backend/codegen.cpp +++ b/src/common/scripting/backend/codegen.cpp @@ -12640,6 +12640,15 @@ FxExpression *FxLocalVariableDeclaration::Resolve(FCompileContext &ctx) if (ValueType->RegType == REGT_NIL && ValueType != TypeAuto) { auto sfunc = static_cast(ctx.Function->Variants[0].Implementation); + + const unsigned MAX_STACK_ALLOC = 512 * 1024; // Windows stack is 1 MB, but we cannot go up there without problems + if (uint64_t(ValueType->Size) + uint64_t(sfunc->ExtraSpace) > MAX_STACK_ALLOC) + { + ScriptPosition.Message(MSG_ERROR, "%s exceeds max. allowed size of 512kb for local variables at variable %s", sfunc->Name.GetChars(), Name.GetChars()); + delete this; + return nullptr; + } + StackOffset = sfunc->AllocExtraStack(ValueType); if (Init != nullptr) diff --git a/src/common/scripting/frontend/zcc_compile.cpp b/src/common/scripting/frontend/zcc_compile.cpp index d109717a32..faef50959c 100644 --- a/src/common/scripting/frontend/zcc_compile.cpp +++ b/src/common/scripting/frontend/zcc_compile.cpp @@ -2286,6 +2286,11 @@ PType *ZCCCompiler::ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, Error(arraysize, "Array size must be positive"); return TypeError; } + if (uint64_t(size) * baseType->Size > 0x7fffffff) + { + Error(arraysize, "Array size overflow. Total size must be less than 2GB"); + return TypeError; + } baseType = NewArray(baseType, size); } diff --git a/src/gamedata/statistics.cpp b/src/gamedata/statistics.cpp index 95d8165ae0..d374f2e8a3 100644 --- a/src/gamedata/statistics.cpp +++ b/src/gamedata/statistics.cpp @@ -343,8 +343,12 @@ static void LevelStatEntry(FSessionStatistics *es, const char *level, const char time (&clock); lt = localtime (&clock); - strcpy(s.name, level); - strcpy(s.info, text); + strncpy(s.name, level, sizeof(s.name) - 1); + s.name[sizeof(s.name) - 1] = '\0'; + + strncpy(s.info, text, sizeof(s.info) - 1); + s.info[sizeof(s.info) - 1] = '\0'; + s.timeneeded=playtime; es->levelstats.Push(s); } diff --git a/src/rendering/hwrenderer/scene/hw_clipper.cpp b/src/rendering/hwrenderer/scene/hw_clipper.cpp index a99752dec7..4b267e2fa5 100644 --- a/src/rendering/hwrenderer/scene/hw_clipper.cpp +++ b/src/rendering/hwrenderer/scene/hw_clipper.cpp @@ -469,8 +469,8 @@ angle_t Clipper::PointToPseudoOrthoAngle(double x, double y) { angle_t af = viewpoint->FrustAngle; double xproj = disp.XY().Length() * deltaangle(disp.Angle(), viewpoint->Angles.Yaw).Sin(); - xproj *= viewpoint->ScreenProj; - if (fabs(xproj) < r_viewwindow.WidescreenRatio*1.13) // 2.0) + xproj *= viewpoint->ScreenProjX; + if (fabs(xproj) < 1.13) { return AngleToPseudo( viewpoint->Angles.Yaw.BAMs() - xproj * 0.5 * af ); } diff --git a/src/rendering/r_utility.cpp b/src/rendering/r_utility.cpp index b7b6b452ba..5313f738c2 100644 --- a/src/rendering/r_utility.cpp +++ b/src/rendering/r_utility.cpp @@ -167,6 +167,7 @@ FRenderViewpoint::FRenderViewpoint() sector = nullptr; FieldOfView = DAngle::fromDeg(90.); // Angles in the SCREENWIDTH wide window ScreenProj = 0.0; + ScreenProjX = 0.0; TicFrac = 0.0; FrameTime = 0; extralight = 0; @@ -704,7 +705,10 @@ void FRenderViewpoint::SetViewAngle(const FViewWindow& viewWindow) HWAngles.Yaw = FAngle::fromDeg(270.0 - Angles.Yaw.Degrees()); if (IsOrtho() && (camera->ViewPos->Offset.XY().Length() > 0.0)) + { ScreenProj = 1.34396 / camera->ViewPos->Offset.Length() / tan (FieldOfView.Radians()*0.5); // [DVR] Estimated. +/-1 should be top/bottom of screen. + ScreenProjX = ScreenProj * 0.5 / viewWindow.WidescreenRatio; + } } diff --git a/src/rendering/r_utility.h b/src/rendering/r_utility.h index ee12ecf366..7beaf14407 100644 --- a/src/rendering/r_utility.h +++ b/src/rendering/r_utility.h @@ -43,6 +43,7 @@ struct FRenderViewpoint sector_t *sector; // [RH] keep track of sector viewing from DAngle FieldOfView; // current field of view double ScreenProj; // Screen projection factor for orthographic projection + double ScreenProjX; // Same for X-axis (screenspace) double TicFrac; // fraction of tic for interpolation uint32_t FrameTime; // current frame's time in tics. diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index dc7fcacc30..cf1d0eca1c 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -385,6 +385,7 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(RF2, CAMFOLLOWSPLAYER, AActor, renderflags2), DEFINE_FLAG(RF2, ISOMETRICSPRITES, AActor, renderflags2), DEFINE_FLAG(RF2, SQUAREPIXELS, AActor, renderflags2), + DEFINE_FLAG(RF2, STRETCHPIXELS, AActor, renderflags2), // Bounce flags DEFINE_FLAG2(BOUNCE_Walls, BOUNCEONWALLS, AActor, BounceFlags), diff --git a/src/scripting/zscript/zcc_compile_doom.cpp b/src/scripting/zscript/zcc_compile_doom.cpp index 3563967e59..a86ea9a0e1 100644 --- a/src/scripting/zscript/zcc_compile_doom.cpp +++ b/src/scripting/zscript/zcc_compile_doom.cpp @@ -724,8 +724,15 @@ void ZCCDoomCompiler::ProcessDefaultProperty(PClassActor *cls, ZCC_PropertyStmt } else if (namenode->SiblingNext->SiblingNext == namenode) { + FName name(namenode->Id); + + if(name == NAME_self) + { + name = cls->TypeName; + } + // a two-name property - propname << FName(namenode->Id).GetChars() << "." << FName(static_cast(namenode->SiblingNext)->Id).GetChars(); + propname << name.GetChars() << "." << FName(static_cast(namenode->SiblingNext)->Id).GetChars(); } else { @@ -784,6 +791,13 @@ void ZCCDoomCompiler::ProcessDefaultFlag(PClassActor *cls, ZCC_FlagStmt *flg) else if (namenode->SiblingNext->SiblingNext == namenode) { // a two-name flag + + if(namenode->Id == NAME_self) + { + n1 = cls->TypeName.GetChars(); + } + + n2 = FName(static_cast(namenode->SiblingNext)->Id).GetChars(); } else