comparison Core/Images/ImageProcessing.cpp @ 3323:a15a4b9d8c00

Added image clipping to <T> FillPolygon_ to prevent out-of-memory access
author Benjamin Golinvaux <bgo@osimis.io>
date Tue, 19 Mar 2019 09:00:34 +0100
parents 59a184cbb596
children 9345710bbf12
comparison
equal deleted inserted replaced
3322:b32b7c44a223 3323:a15a4b9d8c00
1396 int64_t value_) 1396 int64_t value_)
1397 { 1397 {
1398 typedef typename PixelTraits<TargetFormat>::PixelType TargetType; 1398 typedef typename PixelTraits<TargetFormat>::PixelType TargetType;
1399 1399
1400 TargetType value = PixelTraits<TargetFormat>::IntegerToPixel(value_); 1400 TargetType value = PixelTraits<TargetFormat>::IntegerToPixel(value_);
1401 int imageWidth = static_cast<int>(image.GetWidth());
1402 int imageHeight = static_cast<int>(image.GetHeight());
1401 int32_t left; 1403 int32_t left;
1402 int32_t right; 1404 int32_t right;
1403 int32_t top; 1405 int32_t top;
1404 int32_t bottom; 1406 int32_t bottom;
1405 1407
1408 // TODO: test clipping in UT (in Trello board)
1406 ComputePolygonExtent(left, right, top, bottom, points); 1409 ComputePolygonExtent(left, right, top, bottom, points);
1410
1411 // clip the computed extent with the target image
1412 // L and R
1413 left = std::max(0, left);
1414 left = std::min(imageWidth, left);
1415 right = std::max(0, right);
1416 right = std::min(imageWidth, right);
1417 if (left > right)
1418 std::swap(left, right);
1419
1420 // T and B
1421 top = std::max(0, top);
1422 top = std::min(imageHeight, top);
1423 bottom = std::max(0, bottom);
1424 bottom = std::min(imageHeight, bottom);
1425 if (top > bottom)
1426 std::swap(top, bottom);
1407 1427
1408 // from http://alienryderflex.com/polygon_fill/ 1428 // from http://alienryderflex.com/polygon_fill/
1409 1429
1410 // convert all "corner" points to double only once 1430 // convert all "corner" points to double only once
1411 std::vector<double> cpx; 1431 std::vector<double> cpx;
1458 } 1478 }
1459 } 1479 }
1460 1480
1461 TargetType* row = reinterpret_cast<TargetType*>(image.GetRow(pixelY)); 1481 TargetType* row = reinterpret_cast<TargetType*>(image.GetRow(pixelY));
1462 // Fill the pixels between node pairs. 1482 // Fill the pixels between node pairs.
1463 for (i=0; i<nodes; i+=2) 1483 for (i = 0; i < nodes; i += 2)
1464 { 1484 {
1465 if (nodeX[i] >= right) 1485 if (nodeX[i] >= right)
1466 break; 1486 break;
1467 1487
1468 if (nodeX[i+1] >= left) 1488 if (nodeX[i + 1] >= left)
1469 { 1489 {
1470 if (nodeX[i]< left) 1490 if (nodeX[i] < left)
1471 { 1491 {
1472 nodeX[i] = left; 1492 nodeX[i] = left;
1473 } 1493 }
1474 1494
1475 if (nodeX[i+1] > right) 1495 if (nodeX[i + 1] > right)
1476 { 1496 {
1477 nodeX[i+1] = right; 1497 nodeX[i + 1] = right;
1478 } 1498 }
1479 1499
1480 for (pixelX = nodeX[i]; pixelX <= nodeX[i+1]; pixelX++) 1500 for (pixelX = nodeX[i]; pixelX <= nodeX[i + 1]; pixelX++)
1481 { 1501 {
1482 *(row + pixelX) = value; 1502 *(row + pixelX) = value;
1483 } 1503 }
1484 } 1504 }
1485 } 1505 }