Fix potential crashes due to overeager operator[]s

Some operator[]s that know the size of the container they wrap like to assert(index >= 0 && index < size), which is bad for us because we sometimes use &container[size]. This is not undefined behaviour until that pointer is dereferenced, but certain operator[]s choose to ignore this fact and err on the side of caution. The solution is to use &container[0] + size instead of &container[size].
This commit is contained in:
Tamás Bálint Misius 2023-01-07 15:08:50 +01:00
parent c6d6a7d0bf
commit 853c47b0bd
No known key found for this signature in database
GPG Key ID: 5B472A12F6ECA9F2
5 changed files with 29 additions and 29 deletions

View File

@ -2052,7 +2052,7 @@ std::pair<bool, std::vector<char>> GameSave::serialiseOPS() const
unsigned int partsDataLen = 0; unsigned int partsDataLen = 0;
std::vector<unsigned> partsSaveIndex(NPART); std::vector<unsigned> partsSaveIndex(NPART);
unsigned int partsCount = 0; unsigned int partsCount = 0;
std::fill(&partsSaveIndex[0], &partsSaveIndex[NPART], 0); std::fill(&partsSaveIndex[0], &partsSaveIndex[0] + NPART, 0);
for (y=0;y<fullH;y++) for (y=0;y<fullH;y++)
{ {
for (x=0;x<fullW;x++) for (x=0;x<fullW;x++)

View File

@ -1609,7 +1609,7 @@ Renderer::Renderer(Graphics * g, Simulation * sim):
//Prepare the graphics cache //Prepare the graphics cache
graphicscache = new gcache_item[PT_NUM]; graphicscache = new gcache_item[PT_NUM];
std::fill(&graphicscache[0], &graphicscache[PT_NUM], gcache_item()); std::fill(&graphicscache[0], &graphicscache[0] + PT_NUM, gcache_item());
prepare_alpha(CELL, 1.0f); prepare_alpha(CELL, 1.0f);
} }
@ -1630,9 +1630,9 @@ void Renderer::CompileRenderMode()
void Renderer::ClearAccumulation() void Renderer::ClearAccumulation()
{ {
std::fill(fire_r[0]+0, fire_r[(YRES/CELL)-1]+((XRES/CELL)-1), 0); std::fill(&fire_r[0][0], &fire_r[0][0] + (YRES/CELL)*(XRES/CELL), 0);
std::fill(fire_g[0]+0, fire_g[(YRES/CELL)-1]+((XRES/CELL)-1), 0); std::fill(&fire_g[0][0], &fire_g[0][0] + (YRES/CELL)*(XRES/CELL), 0);
std::fill(fire_b[0]+0, fire_b[(YRES/CELL)-1]+((XRES/CELL)-1), 0); std::fill(&fire_b[0][0], &fire_b[0][0] + (YRES/CELL)*(XRES/CELL), 0);
std::fill(persistentVid, persistentVid+(VIDXRES*YRES), 0); std::fill(persistentVid, persistentVid+(VIDXRES*YRES), 0);
} }

View File

@ -261,7 +261,7 @@ int luacon_elementwrite(lua_State* l)
luacon_model->BuildMenus(); luacon_model->BuildMenus();
luacon_sim->init_can_move(); luacon_sim->init_can_move();
std::fill(&luacon_ren->graphicscache[0], &luacon_ren->graphicscache[PT_NUM], gcache_item()); std::fill(&luacon_ren->graphicscache[0], &luacon_ren->graphicscache[0] + PT_NUM, gcache_item());
return 0; return 0;
} }

View File

@ -180,7 +180,7 @@ void Gravity::gravity_update_async()
unsigned int size = (XRES / CELL) * (YRES / CELL); unsigned int size = (XRES / CELL) * (YRES / CELL);
membwand(gravy, gravmask, size * sizeof(float), size * sizeof(unsigned)); membwand(gravy, gravmask, size * sizeof(float), size * sizeof(unsigned));
membwand(gravx, gravmask, size * sizeof(float), size * sizeof(unsigned)); membwand(gravx, gravmask, size * sizeof(float), size * sizeof(unsigned));
std::fill(&gravmap[0], &gravmap[size], 0.0f); std::fill(&gravmap[0], &gravmap[0] + size, 0.0f);
} }
void Gravity::update_grav_async() void Gravity::update_grav_async()
@ -188,11 +188,11 @@ void Gravity::update_grav_async()
int done = 0; int done = 0;
int thread_done = 0; int thread_done = 0;
unsigned int size = (XRES / CELL) * (YRES / CELL); unsigned int size = (XRES / CELL) * (YRES / CELL);
std::fill(&th_ogravmap[0], &th_ogravmap[size], 0.0f); std::fill(&th_ogravmap[0], &th_ogravmap[0] + size, 0.0f);
std::fill(&th_gravmap[0], &th_gravmap[size], 0.0f); std::fill(&th_gravmap[0], &th_gravmap[0] + size, 0.0f);
std::fill(&th_gravy[0], &th_gravy[size], 0.0f); std::fill(&th_gravy[0], &th_gravy[0] + size, 0.0f);
std::fill(&th_gravx[0], &th_gravx[size], 0.0f); std::fill(&th_gravx[0], &th_gravx[0] + size, 0.0f);
std::fill(&th_gravp[0], &th_gravp[size], 0.0f); std::fill(&th_gravp[0], &th_gravp[0] + size, 0.0f);
#ifdef GRAVFFT #ifdef GRAVFFT
if (!grav_fft_status) if (!grav_fft_status)
@ -231,10 +231,10 @@ void Gravity::start_grav_async()
enabled = true; enabled = true;
unsigned int size = (XRES / CELL) * (YRES / CELL); unsigned int size = (XRES / CELL) * (YRES / CELL);
std::fill(&gravy[0], &gravy[size], 0.0f); std::fill(&gravy[0], &gravy[0] + size, 0.0f);
std::fill(&gravx[0], &gravx[size], 0.0f); std::fill(&gravx[0], &gravx[0] + size, 0.0f);
std::fill(&gravp[0], &gravp[size], 0.0f); std::fill(&gravp[0], &gravp[0] + size, 0.0f);
std::fill(&gravmap[0], &gravmap[size], 0.0f); std::fill(&gravmap[0], &gravmap[0] + size, 0.0f);
} }
void Gravity::stop_grav_async() void Gravity::stop_grav_async()
@ -251,10 +251,10 @@ void Gravity::stop_grav_async()
} }
// Clear the grav velocities // Clear the grav velocities
unsigned int size = (XRES / CELL) * (YRES / CELL); unsigned int size = (XRES / CELL) * (YRES / CELL);
std::fill(&gravy[0], &gravy[size], 0.0f); std::fill(&gravy[0], &gravy[0] + size, 0.0f);
std::fill(&gravx[0], &gravx[size], 0.0f); std::fill(&gravx[0], &gravx[0] + size, 0.0f);
std::fill(&gravp[0], &gravp[size], 0.0f); std::fill(&gravp[0], &gravp[0] + size, 0.0f);
std::fill(&gravmap[0], &gravmap[size], 0.0f); std::fill(&gravmap[0], &gravmap[0] + size, 0.0f);
} }
#ifdef GRAVFFT #ifdef GRAVFFT
@ -481,7 +481,7 @@ void Gravity::gravity_mask()
{ {
t_mask_el = new mask_el[sizeof(mask_el)]; t_mask_el = new mask_el[sizeof(mask_el)];
t_mask_el->shape = new char[(XRES / CELL) * (YRES / CELL)]; t_mask_el->shape = new char[(XRES / CELL) * (YRES / CELL)];
std::fill(&t_mask_el->shape[0], &t_mask_el->shape[(XRES / CELL) * (YRES / CELL)], 0); std::fill(&t_mask_el->shape[0], &t_mask_el->shape[0] + (XRES / CELL) * (YRES / CELL), 0);
t_mask_el->shapeout = 0; t_mask_el->shapeout = 0;
t_mask_el->next = nullptr; t_mask_el->next = nullptr;
c_mask_el = t_mask_el; c_mask_el = t_mask_el;
@ -491,7 +491,7 @@ void Gravity::gravity_mask()
c_mask_el->next = new mask_el[sizeof(mask_el)]; c_mask_el->next = new mask_el[sizeof(mask_el)];
c_mask_el = c_mask_el->next; c_mask_el = c_mask_el->next;
c_mask_el->shape = new char[(XRES / CELL) * (YRES / CELL)]; c_mask_el->shape = new char[(XRES / CELL) * (YRES / CELL)];
std::fill(&c_mask_el->shape[0], &c_mask_el->shape[(XRES / CELL) * (YRES / CELL)], 0); std::fill(&c_mask_el->shape[0], &c_mask_el->shape[0] + (XRES / CELL) * (YRES / CELL), 0);
c_mask_el->shapeout = 0; c_mask_el->shapeout = 0;
c_mask_el->next = nullptr; c_mask_el->next = nullptr;
} }
@ -502,7 +502,7 @@ void Gravity::gravity_mask()
} }
} }
c_mask_el = t_mask_el; c_mask_el = t_mask_el;
std::fill(&gravmask[0], &gravmask[(XRES / CELL) * (YRES / CELL)], 0); std::fill(&gravmask[0], &gravmask[0] + (XRES / CELL) * (YRES / CELL), 0);
while (c_mask_el != nullptr) while (c_mask_el != nullptr)
{ {
char *cshape = c_mask_el->shape; char *cshape = c_mask_el->shape;

View File

@ -560,10 +560,10 @@ std::unique_ptr<Snapshot> Simulation::CreateSnapshot()
snap->GravVelocityY .insert (snap->GravVelocityY .begin(), &gravy [0] , &gravy [0] + ((XRES / CELL) * (YRES / CELL))); snap->GravVelocityY .insert (snap->GravVelocityY .begin(), &gravy [0] , &gravy [0] + ((XRES / CELL) * (YRES / CELL)));
snap->GravValue .insert (snap->GravValue .begin(), &gravp [0] , &gravp [0] + ((XRES / CELL) * (YRES / CELL))); snap->GravValue .insert (snap->GravValue .begin(), &gravp [0] , &gravp [0] + ((XRES / CELL) * (YRES / CELL)));
snap->GravMap .insert (snap->GravMap .begin(), &gravmap[0] , &gravmap[0] + ((XRES / CELL) * (YRES / CELL))); snap->GravMap .insert (snap->GravMap .begin(), &gravmap[0] , &gravmap[0] + ((XRES / CELL) * (YRES / CELL)));
snap->Particles .insert (snap->Particles .begin(), &parts [0] , &parts[parts_lastActiveIndex + 1] ); snap->Particles .insert (snap->Particles .begin(), &parts [0] , &parts [0] + parts_lastActiveIndex + 1 );
snap->PortalParticles.insert (snap->PortalParticles.begin(), &portalp[0][0][0], &portalp [CHANNELS - 1][8 - 1][80 - 1] ); snap->PortalParticles.insert (snap->PortalParticles.begin(), &portalp[0][0][0], &portalp[0][0][0] + CHANNELS * 8 * 80 );
snap->WirelessData .insert (snap->WirelessData .begin(), &wireless[0][0] , &wireless[CHANNELS - 1][2 - 1] ); snap->WirelessData .insert (snap->WirelessData .begin(), &wireless[0][0] , &wireless[0][0] + CHANNELS * 2 );
snap->stickmen .insert (snap->stickmen .begin(), &fighters[0] , &fighters[MAX_FIGHTERS] ); snap->stickmen .insert (snap->stickmen .begin(), &fighters[0] , &fighters[0] + MAX_FIGHTERS );
snap->stickmen .push_back(player2); snap->stickmen .push_back(player2);
snap->stickmen .push_back(player); snap->stickmen .push_back(player);
snap->signs = signs; snap->signs = signs;
@ -893,7 +893,7 @@ bool Simulation::flood_water(int x, int y, int i)
// Bitmap for checking where we've already looked // Bitmap for checking where we've already looked
auto bitmapPtr = std::unique_ptr<char[]>(new char[XRES * YRES]); auto bitmapPtr = std::unique_ptr<char[]>(new char[XRES * YRES]);
char *bitmap = bitmapPtr.get(); char *bitmap = bitmapPtr.get();
std::fill(&bitmap[0], &bitmap[XRES * YRES], 0); std::fill(&bitmap[0], &bitmap[0] + XRES * YRES, 0);
try try
{ {
@ -1918,7 +1918,7 @@ int Simulation::FloodParts(int x, int y, int fullc, int cm, int flags)
// Bitmap for checking where we've already looked // Bitmap for checking where we've already looked
auto bitmapPtr = std::unique_ptr<char[]>(new char[XRES * YRES]); auto bitmapPtr = std::unique_ptr<char[]>(new char[XRES * YRES]);
char *bitmap = bitmapPtr.get(); char *bitmap = bitmapPtr.get();
std::fill(&bitmap[0], &bitmap[XRES * YRES], 0); std::fill(&bitmap[0], &bitmap[0] + XRES * YRES, 0);
if (cm==-1) if (cm==-1)
{ {