summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPhilipp Haller <hallerp@gmail.com>2007-05-21 10:09:10 +0000
committerPhilipp Haller <hallerp@gmail.com>2007-05-21 10:09:10 +0000
commit0d4ac84f324c0a8f3cf47761b5e92a3c3ea34ac6 (patch)
tree22b7894e03511b0b8590d46f5a1f62fa124c59a1
parentfc3fb6d5f438d3beb81075168760c500e30c2a55 (diff)
downloadscala-0d4ac84f324c0a8f3cf47761b5e92a3c3ea34ac6.tar.gz
scala-0d4ac84f324c0a8f3cf47761b5e92a3c3ea34ac6.tar.bz2
scala-0d4ac84f324c0a8f3cf47761b5e92a3c3ea34ac6.zip
Ported race condition fix from trunk.
-rw-r--r--src/actors/scala/actors/Actor.scala36
-rw-r--r--src/actors/scala/actors/Reaction.scala8
2 files changed, 26 insertions, 18 deletions
diff --git a/src/actors/scala/actors/Actor.scala b/src/actors/scala/actors/Actor.scala
index 251640dc65..e5db1c5966 100644
--- a/src/actors/scala/actors/Actor.scala
+++ b/src/actors/scala/actors/Actor.scala
@@ -19,7 +19,7 @@ import scala.compat.Platform
* <code>receive</code>, <code>react</code>, <code>reply</code>,
* etc.
*
- * @version 0.9.6
+ * @version 0.9.7
* @author Philipp Haller
*/
object Actor {
@@ -263,7 +263,7 @@ object Actor {
* </li>
* </ul>
*
- * @version 0.9.6
+ * @version 0.9.7
* @author Philipp Haller
*/
trait Actor extends OutputChannel[Any] {
@@ -276,12 +276,18 @@ trait Actor extends OutputChannel[Any] {
private val mailbox = new MessageQueue
private[actors] var sessions: List[Channel[Any]] = Nil
+ private var session1: Option[Channel[Any]] = None
private def send(msg: Any, session: Channel[Any]) = synchronized {
tick()
if (waitingFor(msg)) {
received = Some(msg)
- sessions = session :: sessions
+
+ if (isSuspended)
+ sessions = session :: sessions
+ else
+ session1 = Some(session)
+
waitingFor = waitingForNone
if (timeoutPending) {
@@ -376,7 +382,7 @@ trait Actor extends OutputChannel[Any] {
continuation = f
isDetached = true
} else {
- sessions = qel.session :: sessions
+ session1 = Some(qel.session)
scheduleActor(f, qel.msg)
}
throw new SuspendActorException
@@ -400,7 +406,7 @@ trait Actor extends OutputChannel[Any] {
continuation = f
isDetached = true
} else {
- sessions = qel.session :: sessions
+ session1 = Some(qel.session)
scheduleActor(f, qel.msg)
}
throw new SuspendActorException
@@ -521,13 +527,19 @@ trait Actor extends OutputChannel[Any] {
case x => x
}
- def sender: Actor =
- if (sessions.isEmpty) null
- else sessions.head.asInstanceOf[Channel[Any]].receiver
+ def sender: Actor = {
+ val s = session
+ if (null ne s) s.receiver
+ else null
+ }
private[actors] def session: Channel[Any] =
- if (sessions.isEmpty) null
- else sessions.head.asInstanceOf[Channel[Any]]
+ if (sessions.isEmpty) {
+ session1 match {
+ case None => null
+ case Some(s) => s
+ }
+ } else sessions.head.asInstanceOf[Channel[Any]]
private[actors] var continuation: PartialFunction[Any, Unit] = null
private[actors] var timeoutPending = false
@@ -749,7 +761,7 @@ trait Actor extends OutputChannel[Any] {
* <b>case</b> TIMEOUT <b>=&gt;</b> ...
* }</pre>
*
- * @version 0.9.6
+ * @version 0.9.7
* @author Philipp Haller
*/
case object TIMEOUT
@@ -762,7 +774,7 @@ case class Exit(from: Actor, reason: AnyRef)
* executions.
* </p>
*
- * @version 0.9.6
+ * @version 0.9.7
* @author Philipp Haller
*/
private[actors] class SuspendActorException extends Throwable {
diff --git a/src/actors/scala/actors/Reaction.scala b/src/actors/scala/actors/Reaction.scala
index 02f8283354..8cf8c8c12c 100644
--- a/src/actors/scala/actors/Reaction.scala
+++ b/src/actors/scala/actors/Reaction.scala
@@ -19,7 +19,7 @@ import java.lang.{InterruptedException, Runnable}
* return type <code>Nothing</code>.
* </p>
*
- * @version 0.9.6
+ * @version 0.9.7
* @author Philipp Haller
*/
private[actors] class ExitActorException extends Throwable
@@ -31,7 +31,7 @@ private[actors] class ExitActorException extends Throwable
* <code>java.lang.Runnable</code></a>.
* </p>
*
- * @version 0.9.6
+ * @version 0.9.7
* @author Philipp Haller
*/
private[actors] class Reaction(a: Actor,
@@ -73,10 +73,6 @@ private[actors] class Reaction(a: Actor,
}
}
}
- a.synchronized {
- if (!a.sessions.isEmpty)
- a.sessions = a.sessions.tail
- }
Actor.tl.set(saved)
}