diff --git a/httprl.module b/httprl.module
index 44e02f4..d85e049 100644
--- a/httprl.module
+++ b/httprl.module
@@ -6,6 +6,12 @@
  */
 
 /**
+ * Error code indicating that all requests made by httprl_send_request()
+ * exceeded the specified timeout.
+ */
+define('HTTP_FUNCTION_TIMEOUT', -3);
+
+/**
  * Implement hook_menu().
  */
 function httprl_menu() {
@@ -131,9 +137,9 @@ function httprl_build_url_self($path = '', $detect_schema = FALSE) {
  *     'param=value&param=value&...'. Defaults to NULL.
  *   - max_redirects: An integer representing how many times a redirect
  *     may be followed. Defaults to 3.
- *   - timeout: A float representing the maximum number of seconds the function
- *     call may take. The default is 30 seconds. If a timeout occurs, the error
- *     code is set to the HTTP_REQUEST_TIMEOUT constant.
+ *   - timeout: A float representing the maximum number of seconds a connection
+ *     may take. The default is 30 seconds. If a timeout occurs, the error code
+ *     is set to the HTTP_REQUEST_TIMEOUT constant.
  *   - context: A context resource created with stream_context_create().
  *   - blocking: set to FALSE to make this not care about the returned data.
  *   - version: HTTP Version 1.0 or 1.1. Default is 1.0 for a good reason.
@@ -143,6 +149,10 @@ function httprl_build_url_self($path = '', $detect_schema = FALSE) {
  *     domain name. Default is 8.
  *   - global_connections: Maximum number of simultaneous connections that can
  *     be open on the server. Default is 128.
+ *   - global_timeout: A float representing the maximum number of seconds the
+ *     function call may take. The default is 30 seconds. If a timeout occurs,
+ *     the error code is set to the HTTP_FUNCTION_TIMEOUT constant. Default is
+ *     120 seconds.
  * @return bool
  *   return value from httprl_send_request().
  */
@@ -185,6 +195,7 @@ function httprl_request($url, $options = array()) {
     'referrer' => FALSE,
     'domain_connections' => 8,
     'global_connections' => 128,
+    'global_timeout' => 120.0,
   );
 
   // stream_socket_client() requires timeout to be a float.
@@ -345,7 +356,7 @@ function httprl_request($url, $options = array()) {
 function httprl_send_request($fp = NULL, $url = '', $request = '', $options = '') {
   static $responses = array();
   static $streams = array();
-  static $timeout = 0;
+  static $global_timeout = 0;
   static $counter = 0;
   static $stream_write_count = 0;
   static $global_connection_count = 0;
@@ -367,9 +378,9 @@ function httprl_send_request($fp = NULL, $url = '', $request = '', $options = ''
     // If file pointer is not empty add it to the connection pool.
     if (!empty($fp)) {
       $streams[$counter] = $fp;
-      $timeout = max($options['timeout'], $timeout);
       $stream_write_count++;
       $counter++;
+      $global_timeout = max(1, $options['global_timeout']);
       $global_connection_limit = max(1, $options['global_connections']);
       $domain_connection_limit[$options['headers']['Host']] = max(1, $options['domain_connections']);
       return TRUE;
@@ -390,7 +401,8 @@ function httprl_send_request($fp = NULL, $url = '', $request = '', $options = ''
   }
 
   // Start the timer.
-  timer_start('httprl_send_request');
+  $timer_name = mt_rand();
+  timer_start($timer_name);
 
   // Run the loop as long as we have a stream to read/write to.
   while (!empty($streams)) {
@@ -398,7 +410,7 @@ function httprl_send_request($fp = NULL, $url = '', $request = '', $options = ''
     // Check for timeouts.
     foreach ($streams as $id => $fp) {
       // Calculate how much time is left of the original timeout value.
-      $timeout = $responses[$id]->options['timeout'] - timer_read(__FUNCTION__) / 1000;
+      $timeout = $responses[$id]->options['timeout'] - timer_read($timer_name) / 1000;
       if ($timeout <= 0) {
         if (defined('HTTP_REQUEST_TIMEOUT')) {
           $http_request_timeout = HTTP_REQUEST_TIMEOUT;
@@ -420,6 +432,26 @@ function httprl_send_request($fp = NULL, $url = '', $request = '', $options = ''
         }
       }
     }
+
+    // See if function timed out.
+    $global_time = $global_timeout - timer_read($timer_name) / 1000;
+    if ($global_time <= 0) {
+      foreach ($streams as $id => $fp) {
+        // Function timed out & the request is not done.
+        $responses[$id]->error = 'function timed out';
+        $responses[$id]->code = HTTP_FUNCTION_TIMEOUT;
+        $responses[$id]->status = 'Done.';
+        $responses[$id]->options['timeout'] = $timeout;
+        fclose($fp);
+        unset($streams[$id]);
+        // If stream is not done writing, then remove one from the write count.
+        if ($responses[$id]->status == 'in progress') {
+          $responses[$id]->error = 'request timed out, write';
+          $stream_write_count--;
+        }
+      }
+    }
+
     // All streams timed out.
     if (empty($streams)) {
       break;
@@ -442,7 +474,7 @@ function httprl_send_request($fp = NULL, $url = '', $request = '', $options = ''
         $domain_connection_count[$host]++;
       }
 
-      // If the condtions are correct, let the stream be ran in this loop.
+      // If the conditions are correct, let the stream be ran in this loop.
       if ($global_connection_limit >= $global_connection_count && $domain_connection_limit[$host] >= $domain_connection_count[$host]) {
         $this_run[$id] = $fp;
       }
@@ -579,6 +611,9 @@ function httprl_send_request($fp = NULL, $url = '', $request = '', $options = ''
     }
   }
 
+  // Stop the timer.
+  timer_stop($timer_name);
+
   // HTTP_REQUEST_ALLOWED_REDIRECTS_EXHAUSTED is defined in
   // http://drupal.org/node/1096890
   if (defined('HTTP_REQUEST_ALLOWED_REDIRECTS_EXHAUSTED')) {
@@ -647,12 +682,16 @@ function httprl_send_request($fp = NULL, $url = '', $request = '', $options = ''
     $output[$result->url] = $result;
   }
 
-  // Free memory.
+  // Free memory/reset static variables.
   $responses = array();
   $streams = array();
-  $timeout = 0;
+  $global_timeout = 0;
   $counter = 0;
   $stream_write_count = 0;
+  $global_connection_count = 0;
+  $global_connection_limit = 0;
+  $domain_connection_count = array();
+  $domain_connection_limit = array();
 
   return $output;
 }
