diff --git a/tests/math_expression.test b/tests/math_expression.test
index 942c819..3a33224 100644
--- a/tests/math_expression.test
+++ b/tests/math_expression.test
@@ -27,121 +27,223 @@ class CtoolsMathExpressionTestCase extends DrupalWebTestCase {
   }
 
   /**
-   * Returns a random double between 0 and 1.
+   * Return the sign of the numeric arg $n as an integer -1, 0, 1.
+   *
+   * Note: Not defined when $n is Infinity or NaN (or NULL or ...)!
+   *
+   * @param int|float $n
+   *   The number to test.
+   * @return integer
+   *   -1 if the $n is negative, 0 if $n is zero or 1 if $n is positive.
+   *
+   * @see gmp_sign()
+   */
+  protected static function sign($n) {
+    return ($n > 0) - ($n < 0);
+  }
+
+  /**
+   * Returns a random number between 0 and 1.
+   *
+   * @return float
+   *   A random number between 0 and 1 inclusive.
    */
   protected function rand01() {
-    return rand(0, PHP_INT_MAX) / PHP_INT_MAX;
+    return mt_rand(0, PHP_INT_MAX) / PHP_INT_MAX;
   }
 
   /**
    * A custom assertion with checks the values in a certain range.
+   *
+   * @param float $first
+   *   A value to check for equality.
+   * @param float $second
+   *   A value to check for equality.
+   * @param string $message
+   *   The message describing the correct behaviour, eg. "2/4 equals 1/2". The
+   *   default message is used if this value is empty.
+   * @param float $delta
+   *   The precision with which values must match. This accounts for rounding
+   *   errors and imprecise representation errors in the floating point format.
+   *   The value passed in should ideally be proportional to the values being
+   *   compared.
+   * @param string $group
+   *   Which group this assert belongs to.
+   *
+   * @return bool
+   *   TRUE if the assertion was correct (that is, $first == $second within the
+   *   given limits), FALSE otherwise.
    */
-  protected function assertFloat($first, $second, $delta = 0.0000001, $message = '', $group = 'Other') {
-    return $this->assert(abs($first - $second) <= $delta, $message ? $message : t('Value @first is equal to value @second.', array('@first' => var_export($first, TRUE), '@second' => var_export($second, TRUE))), $group);
+  protected function assertFloat($first, $second, $message = '', $delta = 0.00000001, $group = 'Other') {
+    // Check for NaN and Inf because the abs() and sign() code won't like those.
+    $equal = FALSE
+      // Equal if both an infinity .
+      || (is_infinite($first) && is_infinite($second))
+
+      // Equal if both NaN.
+      || (is_nan($first) && is_nan($second))
+
+      // Equal if same absolute value (within limits) and same sign.
+      || ((abs($first - $second) <= $delta) && (self::sign($first) === self::sign($second)))
+    ;
+
+    if (empty($message)) {
+      $default = t('Value @first is equal to value @second.',
+        array(
+          '@first' => var_export($first, TRUE),
+          '@second' => var_export($second, TRUE)
+        ));
+      $message = $default;
+    }
+
+    return $this->assert($equal, $message, $group);
   }
 
   /**
    * Test some arithmetic handling.
    */
   public function testArithmetic() {
-    $math_expression = new ctools_math_expr();
-
-    // Test constant expressions.
-    $this->assertEqual($math_expression->e('2'), 2);
-    $random_number = rand(0, 10);
-    $this->assertEqual($random_number, $math_expression->e((string) $random_number));
-
-    // Test simple arithmetic.
-    $random_number_a = rand(5, 10);
-    $random_number_b = rand(5, 10);
-    $this->assertEqual($random_number_a + $random_number_b, $math_expression->e("$random_number_a + $random_number_b"));
-    $this->assertEqual($random_number_a - $random_number_b, $math_expression->e("$random_number_a - $random_number_b"));
-    $this->assertEqual($random_number_a * $random_number_b, $math_expression->e("$random_number_a * $random_number_b"));
-    $this->assertEqual($random_number_a / $random_number_b, $math_expression->e("$random_number_a / $random_number_b"));
-
-    // Test Associative property.
-    $random_number_c = rand(5, 10);
-    $this->assertEqual($math_expression->e("$random_number_a + ($random_number_b + $random_number_c)"), $math_expression->e("($random_number_a + $random_number_b) + $random_number_c"));
-    $this->assertEqual($math_expression->e("$random_number_a * ($random_number_b * $random_number_c)"), $math_expression->e("($random_number_a * $random_number_b) * $random_number_c"));
-
-    // Test Commutative property.
-    $this->assertEqual($math_expression->e("$random_number_a + $random_number_b"), $math_expression->e("$random_number_b + $random_number_a"));
-    $this->assertEqual($math_expression->e("$random_number_a * $random_number_b"), $math_expression->e("$random_number_b * $random_number_a"));
-
-    // Test Distributive property.
-    $this->assertEqual($math_expression->e("($random_number_a + $random_number_b) * $random_number_c"), $math_expression->e("($random_number_a * $random_number_c + $random_number_b * $random_number_c)"));
-
-    $this->assertEqual(pow($random_number_a, $random_number_b), $math_expression->e("$random_number_a ^ $random_number_b"));
+    $math_expr = new ctools_math_expr();
+
+    $this->assertEqual($math_expr->e('2'), 2, 'Literal 2');
+
+    foreach (range(1, 4) as $n) {
+      // Test constant expressions.
+      $random_number = mt_rand(0, 20);
+      $this->assertEqual($random_number, $math_expr->e((string) $random_number), "Literal $random_number");
+
+      // Test simple arithmetic.
+      $random_number_a = mt_rand(-55, 777);
+      $random_number_b = mt_rand(-555, 77);
+      $this->assertEqual(
+        $random_number_a + $random_number_b,
+        $math_expr->e("$random_number_a + $random_number_b"),
+        "Addition: $random_number_a + $random_number_b");
+      $this->assertEqual(
+        $random_number_a - $random_number_b,
+        $math_expr->e("$random_number_a - $random_number_b"),
+        "Subtraction: $random_number_a + $random_number_b");
+      $this->assertEqual(
+        $random_number_a * $random_number_b,
+        $math_expr->e("$random_number_a * $random_number_b"),
+        "Multiplication: $random_number_a * $random_number_b");
+      $this->assertEqual(
+        $random_number_a / $random_number_b,
+        $math_expr->e("$random_number_a / $random_number_b"),
+        "Division: $random_number_a / $random_number_b");
+
+      // Test Associative property.
+      $random_number_c = mt_rand(-99, 77);
+      $this->assertEqual(
+        $math_expr->e("$random_number_a + ($random_number_b + $random_number_c)"),
+        $math_expr->e("($random_number_a + $random_number_b) + $random_number_c"),
+        "Associative: $random_number_a + ($random_number_b + $random_number_c");
+      $this->assertEqual(
+        $math_expr->e("$random_number_a * ($random_number_b * $random_number_c)"),
+        $math_expr->e("($random_number_a * $random_number_b) * $random_number_c"),
+        "Associative: $random_number_a * ($random_number_b * $random_number_c");
+
+      // Test Commutative property.
+      $this->assertEqual(
+        $math_expr->e("$random_number_a + $random_number_b"),
+        $math_expr->e("$random_number_b + $random_number_a"),
+        "Commutative: $random_number_a + $random_number_b");
+      $this->assertEqual(
+        $math_expr->e("$random_number_a * $random_number_b"),
+        $math_expr->e("$random_number_b * $random_number_a"),
+        "Commutative: $random_number_a * $random_number_b");
+
+      // Test Distributive property.
+      $this->assertEqual(
+        $math_expr->e("($random_number_a + $random_number_b) * $random_number_c"),
+        $math_expr->e("($random_number_a * $random_number_c + $random_number_b * $random_number_c)"),
+        "Distributive: ($random_number_a + $random_number_b) * $random_number_c");
+
+      $random_number = mt_rand(0, 15);
+      $random_power = mt_rand(-15, 15);
+      $this->assertEqual(
+        pow($random_number, $random_power),
+        $math_expr->e("$random_number ^ $random_power"),
+        "pow($random_number, $random_power)");
+    }
   }
 
   /**
-   * Test 
+   * Test various built-in transcendental and extended functions.
    */
   public function testBuildInFunctions() {
-    $math_expression = new ctools_math_expr();
+    $math_expr = new ctools_math_expr();
 
     // @todo Maybe run this code multiple times to test different values.
-    $random_double = $this->rand01();
-    $random_int = rand(5, 10);
-    $this->assertFloat(sin($random_double), $math_expression->e("sin($random_double)"));
-    $this->assertFloat(cos($random_double), $math_expression->e("cos($random_double)"));
-    $this->assertFloat(tan($random_double), $math_expression->e("tan($random_double)"));
-    $this->assertFloat(exp($random_double), $math_expression->e("exp($random_double)"));
-    $this->assertFloat(sqrt($random_double), $math_expression->e("sqrt($random_double)"));
-    $this->assertFloat(log($random_double), $math_expression->e("ln($random_double)"));
-    $this->assertFloat(round($random_double), $math_expression->e("round($random_double)"));
-    $this->assertFloat(abs($random_double + $random_int), $math_expression->e('abs(' . ($random_double + $random_int) . ')'));
-    $this->assertEqual(round($random_double + $random_int), $math_expression->e('round(' . ($random_double + $random_int) . ')'));
-    $this->assertEqual(ceil($random_double + $random_int), $math_expression->e('ceil(' . ($random_double + $random_int) . ')'));
-    $this->assertEqual(floor($random_double + $random_int), $math_expression->e('floor(' . ($random_double + $random_int) . ')'));
-
-    // @fixme: you can't run time without an argument.
-    $this->assertFloat(time(), $math_expression->e('time(1)'));
-
-    $random_double_a = $this->rand01();
-    $random_double_b = $this->rand01();
-    // @fixme: max/min don't work at the moment.
-//    $this->assertFloat(max($random_double_a, $random_double_b), $math_expression->e("max($random_double_a, $random_double_b)"));
-//    $this->assertFloat(min($random_double_a, $random_double_b), $math_expression->e("min($random_double_a, $random_double_b)"));
+    foreach (range(1, 4) as $n) {
+      $random_double = $this->rand01();
+      $random_int = mt_rand(-65535, 65535);
+      $this->assertFloat(sin($random_double), $math_expr->e("sin($random_double)"), "sin($random_double)");
+      $this->assertFloat(cos($random_double), $math_expr->e("cos($random_double)"), "cos($random_double)");
+      $this->assertFloat(tan($random_double), $math_expr->e("tan($random_double)"), "tan($random_double)");
+      $this->assertFloat(exp($random_double), $math_expr->e("exp($random_double)"), "exp($random_double)");
+      $this->assertFloat(sqrt($random_double), $math_expr->e("sqrt($random_double)"), "sqrt($random_double)");
+      $this->assertFloat(log($random_double), $math_expr->e("ln($random_double)"), "ln($random_double)");
+      $this->assertFloat(round($random_double), $math_expr->e("round($random_double)"), "round($random_double)");
+
+      $random_real = $random_double + $random_int;
+      $this->assertFloat(abs($random_real), $math_expr->e('abs(' . $random_real . ')'), "abs($random_real)");
+      $this->assertEqual(round($random_real), $math_expr->e('round(' . $random_real . ')'), "round($random_real)");
+      $this->assertEqual(ceil($random_real), $math_expr->e('ceil(' . $random_real . ')'), "ceil($random_real)");
+      $this->assertEqual(floor($random_real), $math_expr->e('floor(' . $random_real . ')'), "floor($random_real)");
+    }
+
+    $this->assertFloat(time(), $math_expr->e('time(1)'), "time(1)");
   }
 
   /**
    * Test variable handling.
    */
   public function testVariables() {
-    $math_expression = new ctools_math_expr();
+    $math_expr = new ctools_math_expr();
+
+    // We should have a definition of pi:
+    $this->assertEqual(3.1415926535897931, $math_expr->e('pi'));
+
+    // and a definition of e:
+    $this->assertEqual(2.7182818284590451, $math_expr->e('e'));
+
+    $number_a = 5;
+    $number_b = 10;
 
-    $random_number_a = rand(5, 10);
-    $random_number_b = rand(5, 10);
+    // Store the first number and use it on a calculation.
+    $math_expr->e("var = $number_a");
+    $this->assertEqual($number_a + $number_b, $math_expr->e("var + $number_b"));
+    // Change the value and check the new value is used.
+    $math_expr->e("var = $number_b");
+    $this->assertEqual($number_b + $number_b, $math_expr->e("var + $number_b"));
 
-    // Store the first random number and use it on calculations.
-    $math_expression->e("var = $random_number_a");
-    $this->assertEqual($random_number_a + $random_number_b, $math_expression->e("var + $random_number_b"));
-    $this->assertEqual($random_number_a * $random_number_b, $math_expression->e("var * $random_number_b"));
-    $this->assertEqual($random_number_a - $random_number_b, $math_expression->e("var - $random_number_b"));
-    $this->assertEqual($random_number_a / $random_number_b, $math_expression->e("var / $random_number_b"));
+    // Store another number and use it on a calculation.
+    $math_expr->e("var = $number_a");
+    $math_expr->e("newvar = $number_a");
+    $this->assertEqual($number_a + $number_a, $math_expr->e('var + newvar'));
   }
 
   /**
    * Test custom function handling.
    */
   public function testCustomFunctions() {
-    $math_expression = new ctools_math_expr();
+    $math_expr = new ctools_math_expr();
 
-    $random_number_a = rand(5, 10);
-    $random_number_b = rand(5, 10);
+    $random_number_a = mt_rand(5, 10);
+    $random_number_b = mt_rand(5, 10);
 
     // Create a one-argument function.
-    $math_expression->e("f(x) = 2 * x");
-    $this->assertEqual($random_number_a * 2, $math_expression->e("f($random_number_a)"));
-    $this->assertEqual($random_number_b * 2, $math_expression->e("f($random_number_b)"));
+    $math_expr->e("f(x) = 2 * x");
+    $this->assertEqual($random_number_a * 2, $math_expr->e("f($random_number_a)"));
+    $this->assertEqual($random_number_b * 2, $math_expr->e("f($random_number_b)"));
 
     // Create a two-argument function.
-    $math_expression->e("g(x, y) = 2 * x + y");
-    $this->assertEqual($random_number_a * 2 + $random_number_b, $math_expression->e("g($random_number_a, $random_number_b)"));
+    $math_expr->e("g(x, y) = 2 * x + y");
+    $this->assertEqual($random_number_a * 2 + $random_number_b, $math_expr->e("g($random_number_a, $random_number_b)"));
 
     // Use a custom function in another function.
-    $this->assertEqual(($random_number_a * 2 + $random_number_b) * 2, $math_expression->e("f(g($random_number_a, $random_number_b))"));
+    $this->assertEqual(($random_number_a * 2 + $random_number_b) * 2, $math_expr->e("f(g($random_number_a, $random_number_b))"));
   }
 
 }
