Index: Stackless/unittests/test_channel.py
===================================================================
--- Stackless/unittests/test_channel.py	(revision 76627)
+++ Stackless/unittests/test_channel.py	(working copy)
@@ -105,7 +105,39 @@
         c = stackless.channel()
         self.failUnlessRaises(RuntimeError, c.receive)
 
+    def testSendException(self):
+        ''' Test that an exception sent across a channel will be received as a raised exception. '''
 
+        # Function to send an exception.
+        def f(testChannel, exceptionToSend):
+            try:
+                raise exceptionToSend
+            except Exception as e:
+                testChannel.send_exception(e)
+
+        class ExpectedError(Exception):
+            pass
+
+        # Get the tasklet blocked on the channel.
+        channel = stackless.channel()
+        tasklet = stackless.tasklet(f)(channel, ExpectedError())
+        tasklet.run()
+
+        try:
+            # This will raise an exception
+            channel.receive()
+            self.fail("Receive should throw an exception")
+        except ExpectedError as e:
+            # The exception should have a traceback indicating its source
+            import traceback
+            tb = traceback.extract_tb(e.__traceback__)
+            self.assertEqual(len(tb), 2, "Traceback should contain full stack information")
+            self.assertEqual(tb[-1][2], 'f', "Traceback should be preserved for an exception sent across a channel")
+        else:
+            self.fail("Should have received an exeption of type ExpectedError")
+
+        tasklet.kill()
+
 if __name__ == '__main__':
     import sys
     if not sys.argv[1:]:
Index: Stackless/module/taskletobject.c
===================================================================
--- Stackless/module/taskletobject.c	(revision 76627)
+++ Stackless/module/taskletobject.c	(working copy)
@@ -855,7 +855,7 @@
 
 static char tasklet_raise_exception__doc__[] =
 "tasklet.raise_exception(exc, value) -- raise an exception for the tasklet.\n\
-exc must be a subclass of Exception.\n\
+exc must be a type or instance of a type subclassing from Exception.\n\
 The tasklet is immediately activated.";
 
 static PyObject *
@@ -906,12 +906,44 @@
 {
 	STACKLESS_GETARG();
 	PyObject *result = NULL;
-	PyObject *klass = PySequence_GetItem(args, 0);
+	PyObject *klass = NULL;
+	PyObject *klass_or_instance = PySequence_GetItem(args, 0);
 
-	if (klass == NULL)
-		VALUE_ERROR("tasklet.raise_exception(e, v...)", NULL);
-	args = PySequence_GetSlice(args, 1, PySequence_Size(args));
-	if (!args) goto err_exit;
+	if (klass_or_instance == NULL)
+		VALUE_ERROR("tasklet.raise_exception(e, [v...])", NULL);
+
+	/* Normalize arguments to impl_tasklet_raise_exception */
+	if (PyExceptionClass_Check(klass_or_instance))
+	{
+		/* If args[0] is an exception class, the rest of the arguments
+		   are treated as initialization parameters. */
+		klass = klass_or_instance;
+		args = PySequence_GetSlice(args, 1, PySequence_Size(args));
+		if (!args) goto err_exit;
+	}
+	else if (PyExceptionInstance_Check(klass_or_instance))
+	{
+		/* If args[0] is an exception instance, klass is extracted
+		   from the instance. */
+		if (PySequence_Length(args) != 1)
+		{
+			Py_DECREF(klass_or_instance);
+			VALUE_ERROR("channel.send_exception(e, [v...])\n"
+				"If e is an exception instance, no other "
+				"arguments may be provided.", NULL);
+		}
+		klass = PyExceptionInstance_Class(klass_or_instance);
+		Py_INCREF(klass);
+		args = klass_or_instance;
+	}
+	else
+	{
+		Py_DECREF(klass_or_instance);
+		VALUE_ERROR("tasklet.raise_exception(e, [v...])\n"
+			"e must be a type or instance of a "
+			"type subclassing from Exception.", NULL);
+	}
+
 	STACKLESS_PROMOTE_ALL();
 	result = impl_tasklet_raise_exception(
 	    (PyTaskletObject*)myself, klass, args);
Index: Stackless/module/channelobject.c
===================================================================
--- Stackless/module/channelobject.c	(revision 76627)
+++ Stackless/module/channelobject.c	(working copy)
@@ -499,7 +499,7 @@
 
 static char channel_send_exception__doc__[] =
 "channel.send_exception(exc, value) -- send an exception over the channel.\n\
-exc must be a subclass of Exception.\n\
+exc must be a type or instance of a type subclassing from Exception.\n\
 Behavior is like channel.send, but that the receiver gets an exception.";
 
 static PyObject *
@@ -547,14 +547,46 @@
 {
 	STACKLESS_GETARG();
 	PyObject *retval = NULL;
-	PyObject *klass = PySequence_GetItem(args, 0);
+	PyObject *klass = NULL;
+	PyObject *klass_or_instance = PySequence_GetItem(args, 0);
 
-	if (klass == NULL)
-		VALUE_ERROR("channel.send_exception(e, v...)", NULL);
-	args = PySequence_GetSlice(args, 1, PySequence_Size(args));
-	if (!args) {
-		goto err_exit;
+	if (klass_or_instance == NULL)
+		VALUE_ERROR("channel.send_exception(e, [v...])", NULL);
+
+	/* Normalize arguments to impl_channel_send_exception */
+	if (PyExceptionClass_Check(klass_or_instance))
+	{
+		/* If args[0] is an exception class, the rest of the arguments
+		   are treated as initialization parameters. */
+		klass = klass_or_instance;
+		args = PySequence_GetSlice(args, 1, PySequence_Size(args));
+		if (!args) {
+			goto err_exit;
+		}
 	}
+	else if (PyExceptionInstance_Check(klass_or_instance))
+	{
+		/* If args[0] is an exception instance, klass is extracted
+		   from the instance. */
+		if (PySequence_Length(args) != 1)
+		{
+			Py_DECREF(klass_or_instance);
+			VALUE_ERROR("channel.send_exception(e, [v...])\n"
+				"If e is an exception instance, no other "
+				"arguments may be provided.", NULL);
+		}
+		klass = PyExceptionInstance_Class(klass_or_instance);
+		Py_INCREF(klass);
+		args = klass_or_instance;
+	}
+	else
+	{
+		Py_DECREF(klass_or_instance);
+		VALUE_ERROR("channel.send_exception(e, [v...])\n"
+			"e must be a type or instance of a "
+			"type subclassing from Exception.", NULL);
+	}
+
 	STACKLESS_PROMOTE_ALL();
 	retval = impl_channel_send_exception((PyChannelObject*)myself,
 						klass, args);
Index: Stackless/module/scheduling.c
===================================================================
--- Stackless/module/scheduling.c	(revision 76627)
+++ Stackless/module/scheduling.c	(working copy)
@@ -123,12 +123,22 @@
 		return NULL;
 	Py_INCREF(klass);
 	bomb->curexc_type = klass;
-	tup = Py_BuildValue(PyTuple_Check(args) ? "O" : "(O)", args);
-	bomb->curexc_value = tup;
-	if (tup == NULL) {
-		Py_DECREF(bomb);
-		return NULL;
+
+	if (PyExceptionInstance_Check(args))
+	{
+		Py_INCREF(args);
+		bomb->curexc_value = args;
+		bomb->curexc_traceback = PyException_GetTraceback(args);
 	}
+	else
+	{
+		tup = Py_BuildValue(PyTuple_Check(args) ? "O" : "(O)", args);
+		bomb->curexc_value = tup;
+		if (tup == NULL) {
+			Py_DECREF(bomb);
+			return NULL;
+		}
+	}
 	return (PyObject *) bomb;
 }
 
