about summary refs log tree commit diff
diff options
context:
space:
mode:
authorgiraffedata <giraffedata@9d0c8265-081b-0410-96cb-a4ca84ce46f8>2023-09-06 23:20:19 +0000
committergiraffedata <giraffedata@9d0c8265-081b-0410-96cb-a4ca84ce46f8>2023-09-06 23:20:19 +0000
commit6c8b9ea2f03aa6cc250dd80a0d6232c8c4449cb7 (patch)
tree5ab8e5f0a109da13c3a575e3fc281bf86a777d2b
parentcacc48b5dc3fe179980070a26cd9da03308708d6 (diff)
downloadnetpbm-mirror-6c8b9ea2f03aa6cc250dd80a0d6232c8c4449cb7.tar.gz
netpbm-mirror-6c8b9ea2f03aa6cc250dd80a0d6232c8c4449cb7.tar.xz
netpbm-mirror-6c8b9ea2f03aa6cc250dd80a0d6232c8c4449cb7.zip
Release 11.03.05
git-svn-id: http://svn.code.sf.net/p/netpbm/code/advanced@4636 9d0c8265-081b-0410-96cb-a4ca84ce46f8
-rw-r--r--converter/other/pamtosvg/fit.c42
-rw-r--r--doc/HISTORY13
-rw-r--r--editor/pamaddnoise.c41
-rw-r--r--generator/ppmrough.c46
-rw-r--r--version.mk2
5 files changed, 83 insertions, 61 deletions
diff --git a/converter/other/pamtosvg/fit.c b/converter/other/pamtosvg/fit.c
index 179b3bdf..06e708c2 100644
--- a/converter/other/pamtosvg/fit.c
+++ b/converter/other/pamtosvg/fit.c
@@ -1379,14 +1379,26 @@ findHalfTangentBeg(curve *      const curveP,
         unsigned int const thisIndex = p + 1;
         float_coord  const thisPoint = CURVE_POINT(curveP, thisIndex);
 
-        /* Perhaps we should weight the tangent from `thisPoint' by some
-           factor dependent on the distance from the tangent point.
-        */
-        sum = Vadd(sum, Pdirection(thisPoint, tangentPoint));
-        ++n;
+        if (epsilon_equal(thisPoint.x, tangentPoint.x) &&
+            epsilon_equal(thisPoint.y, tangentPoint.y) &&
+            epsilon_equal(thisPoint.z, tangentPoint.z)) {
+            /* It's the same point; can't compute a slope */
+        } else {
+            /* Perhaps we should weight the tangent from `thisPoint' by some
+               factor dependent on the distance from the tangent point.
+            */
+            sum = Vadd(sum, Pdirection(thisPoint, tangentPoint));
+            ++n;
+        }
     }
 
-    mean = Vmult_scalar(sum, 1.0 / n);
+    if (n >= 1)
+        mean = Vmult_scalar(sum, 1.0 / n);
+    else {
+        mean.dx = 1.0;
+        mean.dy = 0.0;
+        mean.dz = 0.0;
+    }
 
     return mean;
 }
@@ -1418,11 +1430,23 @@ findHalfTangentEnd(curve *      const curveP,
         unsigned int const thisIndex = CURVE_LENGTH(curveP) - 1 - p;
         float_coord  const thisPoint = CURVE_POINT(curveP, thisIndex);
 
-        sum = Vadd(sum, Pdirection(tangentPoint, thisPoint));
-        ++n;
+        if (epsilon_equal(thisPoint.x, tangentPoint.x) &&
+            epsilon_equal(thisPoint.y, tangentPoint.y) &&
+            epsilon_equal(thisPoint.z, tangentPoint.z)) {
+            /* It's the same point; can't compute a slope */
+        } else {
+            sum = Vadd(sum, Pdirection(tangentPoint, thisPoint));
+            ++n;
+        }
     }
 
-    mean = Vmult_scalar(sum, 1.0 / n);
+    if (n >= 1)
+        mean = Vmult_scalar(sum, 1.0 / n);
+    else {
+        mean.dx = 1.0;
+        mean.dy = 0.0;
+        mean.dz = 0.0;
+    }
 
     return mean;
 }
diff --git a/doc/HISTORY b/doc/HISTORY
index be97732d..dc7f78c4 100644
--- a/doc/HISTORY
+++ b/doc/HISTORY
@@ -4,6 +4,19 @@ Netpbm.
 CHANGE HISTORY 
 --------------
 
+23.09.06 BJH  Release 11.03.05
+
+              pamtosvg: fix hang.
+
+              pamaddnoise: fix very incorrect noise added for all types.
+              Introduced in Netpbm 10.94 (March 2021).
+
+              ppmrough: fix buffer overrun.  Always broken (Ppmrough was new
+              in Netpbm 10.9 (September 2002).
+
+              ppmrough: fix excessive roughness.  Introduced in Netpbm 10.94
+              (March 2021).
+
 23.08.20 BJH  Release 11.03.04
 
               pgmtexture: Fix buffer overflow with maxval > 255.  Always
diff --git a/editor/pamaddnoise.c b/editor/pamaddnoise.c
index 9ca80394..e585700b 100644
--- a/editor/pamaddnoise.c
+++ b/editor/pamaddnoise.c
@@ -43,14 +43,6 @@ static double const SALT_RATIO = 0.5;
 
 
 
-static double
-rand1(struct pm_randSt * const randStP) {
-
-    return (double)pm_rand(randStP)/RAND_MAX;
-}
-
-
-
 enum NoiseType {
     NOISETYPE_GAUSSIAN,
     NOISETYPE_IMPULSE,  /* aka salt and pepper noise */
@@ -226,19 +218,13 @@ addGaussianNoise(sample             const maxval,
    Based on Kasturi/Algorithms of the ACM
 -----------------------------------------------------------------------------*/
 
-    double x1, x2, xn, yn;
+    double grnd1, grnd2; /* Gaussian random numbers.  mean=0 sigma=1 */
     double rawNewSample;
 
-    x1 = rand1(randStP);
-
-    if (x1 == 0.0)
-        x1 = 1.0;
-    x2 = rand1(randStP);
-    xn = sqrt(-2.0 * log(x1)) * cos(2.0 * M_PI * x2);
-    yn = sqrt(-2.0 * log(x1)) * sin(2.0 * M_PI * x2);
+    pm_gaussrand2(randStP, &grnd1, &grnd2);
 
     rawNewSample =
-        origSample + (sqrt((double) origSample) * sigma1 * xn) + (sigma2 * yn);
+      origSample + (sqrt((double) origSample) * sigma1 * grnd1) + (sigma2 * grnd2);
 
     *newSampleP = MAX(MIN((int)rawNewSample, maxval), 0);
 }
@@ -259,7 +245,7 @@ addImpulseNoise(sample             const maxval,
     double const pepperRatio = 1.0 - saltRatio;
     double const loTolerance = tolerance * pepperRatio;
     double const hiTolerance = 1.0 - tolerance * saltRatio;
-    double const sap         = rand1(randStP);
+    double const sap         = pm_drand(randStP);
 
     *newSampleP =
         sap < loTolerance ? 0 :
@@ -281,7 +267,7 @@ addLaplacianNoise(sample             const maxval,
 
    From Pitas' book.
 -----------------------------------------------------------------------------*/
-    double const u = rand1(randStP);
+    double const u = pm_drand(randStP);
 
     double rawNewSample;
 
@@ -314,21 +300,10 @@ addMultiplicativeGaussianNoise(sample             const maxval,
 
    From Pitas' book.
 -----------------------------------------------------------------------------*/
-    double rayleigh, gauss;
+
     double rawNewSample;
 
-    {
-        double const uniform = rand1(randStP);
-        if (uniform <= EPSILON)
-            rayleigh = infinity;
-        else
-            rayleigh = sqrt(-2.0 * log( uniform));
-    }
-    {
-        double const uniform = rand1(randStP);
-        gauss = rayleigh * cos(2.0 * M_PI * uniform);
-    }
-    rawNewSample = origSample + (origSample * mgsigma * gauss);
+    rawNewSample = origSample + (origSample * mgsigma * pm_gaussrand(randStP));
 
     *newSampleP = MIN(MAX((int)rawNewSample, 0), maxval);
 }
@@ -384,7 +359,7 @@ addPoissonNoise(struct pam *       const pamP,
 
     double const lambda  = origSampleIntensity * lambdaOfMaxval;
 
-    double const u = rand1(randStP);
+    double const u = pm_drand(randStP);
 
     /* We now apply the inverse CDF (cumulative distribution function) of the
        Poisson distribution to uniform random variable 'u' to get a Poisson
diff --git a/generator/ppmrough.c b/generator/ppmrough.c
index a4a1f14d..c43b1fa5 100644
--- a/generator/ppmrough.c
+++ b/generator/ppmrough.c
@@ -96,6 +96,14 @@ parseCommandLine(int argc, const char ** argv,
         cmdlineP->fg = NULL;
     if (!varSpec)
         cmdlineP->var = 10;
+    if (cmdlineP->topSpec && cmdlineP->top > cmdlineP->height)
+        pm_error("-top value too large.  Max is %u", cmdlineP->height);
+    if (cmdlineP->bottomSpec && cmdlineP->bottom > cmdlineP->height)
+        pm_error("-bottom value too large.  Max is %u", cmdlineP->height);
+    if (cmdlineP->leftSpec && cmdlineP->left > cmdlineP->width)
+        pm_error("-left value too large.  Max is %u", cmdlineP->width);
+    if (cmdlineP->rightSpec && cmdlineP->right > cmdlineP->width)
+        pm_error("-right value too large.  Max is %u", cmdlineP->width);
 
     if (argc-1 != 0)
         pm_error("There are no arguments.  You specified %d.", argc-1);
@@ -159,6 +167,7 @@ procLeft(pixel **           const pixels,
          int                const r2,
          int                const c1,
          int                const c2,
+         unsigned int       const width,
          unsigned int       const var,
          pixel              const bgcolor,
          struct pm_randSt * const randStP) {
@@ -166,15 +175,15 @@ procLeft(pixel **           const pixels,
     if (r1 + 1 != r2) {
         int const rm = (r1 + r2) >> 1;
         int const cm = ((c1 + c2) >> 1) +
-            (int)floor(((float)pm_rand(randStP) / RAND_MAX - 0.5) * var + 0.5);
+            (int)floor(((float)pm_drand(randStP) - 0.5) * var + 0.5);
 
-        int c;
+        unsigned int c;
 
-        for (c = 0; c < cm; c++)
+        for (c = 0; c < MIN(width, MAX(0, cm)); c++)
             pixels[rm][c] = bgcolor;
 
-        procLeft(pixels, r1, rm, c1, cm, var, bgcolor, randStP);
-        procLeft(pixels, rm, r2, cm, c2, var, bgcolor, randStP);
+        procLeft(pixels, r1, rm, c1, cm, width, var, bgcolor, randStP);
+        procLeft(pixels, rm, r2, cm, c2, width, var, bgcolor, randStP);
     }
 }
 
@@ -194,11 +203,11 @@ procRight(pixel **           const pixels,
     if (r1 + 1 != r2) {
         int const rm = (r1 + r2) >> 1;
         int const cm = ((c1 + c2) >> 1) +
-            (int)floor(((float)pm_rand(randStP) / RAND_MAX - 0.5) * var + 0.5);
+            (int)floor(((float)pm_drand(randStP) - 0.5) * var + 0.5);
 
-        int c;
+        unsigned int c;
 
-        for (c = cm; c < width; c++)
+        for (c = MAX(0, cm); c < width; c++)
             pixels[rm][c] = bgcolor;
 
         procRight(pixels, r1, rm, c1, cm, width, var, bgcolor, randStP);
@@ -214,6 +223,7 @@ procTop(pixel **           const pixels,
         int                const c2,
         int                const r1,
         int                const r2,
+        unsigned int       const height,
         unsigned int       const var,
         pixel              const bgcolor,
         struct pm_randSt * const randStP) {
@@ -221,15 +231,15 @@ procTop(pixel **           const pixels,
     if (c1 + 1 != c2) {
         int const cm = (c1 + c2) >> 1;
         int const rm = ((r1 + r2) >> 1) +
-            (int)floor(((float)pm_rand(randStP) / RAND_MAX - 0.5) * var + 0.5);
+            (int)floor(((float)pm_drand(randStP) - 0.5) * var + 0.5);
 
-        int r;
+        unsigned int r;
 
-        for (r = 0; r < rm; r++)
+        for (r = 0; r < MIN(height, MAX(0, rm)); r++)
             pixels[r][cm] = bgcolor;
 
-        procTop(pixels, c1, cm, r1, rm, var, bgcolor, randStP);
-        procTop(pixels, cm, c2, rm, r2, var, bgcolor, randStP);
+        procTop(pixels, c1, cm, r1, rm, height, var, bgcolor, randStP);
+        procTop(pixels, cm, c2, rm, r2, height, var, bgcolor, randStP);
     }
 }
 
@@ -249,11 +259,11 @@ procBottom(pixel **           const pixels,
     if (c1 + 1 != c2) {
         int const cm = (c1 + c2) >> 1;
         int const rm = ((r1 + r2) >> 1) +
-            (int)floor(((float)pm_rand(randStP) / RAND_MAX - 0.5) * var + 0.5);
+            (int)floor(((float)pm_drand(randStP) - 0.5) * var + 0.5);
 
-        int r;
+        unsigned int r;
 
-        for (r = rm; r < height; ++r)
+        for (r = MAX(0, rm); r < height; ++r)
             pixels[r][cm] = bgcolor;
 
         procBottom(pixels, c1, cm, r1, rm, height, var, bgcolor, randStP);
@@ -286,7 +296,7 @@ makeRaggedLeftBorder(pixel **           const pixels,
         for (col = 0; col < leftC2; ++col)
             pixels[leftR2][col] = bgcolor;
 
-        procLeft(pixels, leftR1, leftR2, leftC1, leftC2, var,
+        procLeft(pixels, leftR1, leftR2, leftC1, leftC2, cols, var,
                  bgcolor, randStP);
     }
 }
@@ -347,7 +357,7 @@ makeRaggedTopBorder(pixel **           const pixels,
         for (row = 0; row < topR2; ++row)
             pixels[row][topC2] = bgcolor;
 
-        procTop(pixels, topC1, topC2, topR1, topR2, var, bgcolor, randStP);
+        procTop(pixels, topC1, topC2, topR1, topR2, rows, var, bgcolor, randStP);
     }
 }
 
diff --git a/version.mk b/version.mk
index c1f267cc..0f13782a 100644
--- a/version.mk
+++ b/version.mk
@@ -1,3 +1,3 @@
 NETPBM_MAJOR_RELEASE = 11
 NETPBM_MINOR_RELEASE = 3
-NETPBM_POINT_RELEASE = 4
+NETPBM_POINT_RELEASE = 5