This is an automated email from the ASF dual-hosted git repository.
markt pushed a commit to branch 8.5.x
in repository https://gitbox.apache.org/repos/asf/tomcat.git
The following commit(s) were added to refs/heads/8.5.x by this push:
new 9c7aff6 Update state definitions and associated diagram (now a lot
simpler)
9c7aff6 is described below
commit 9c7aff63fc848ab0db425499a62177ec2dc009ad
Author: Mark Thomas <[email protected]>
AuthorDate: Thu Oct 17 22:32:17 2019 +0100
Update state definitions and associated diagram (now a lot simpler)
---
java/org/apache/coyote/AsyncStateMachine.java | 167 ++++++++++++--------------
1 file changed, 75 insertions(+), 92 deletions(-)
diff --git a/java/org/apache/coyote/AsyncStateMachine.java
b/java/org/apache/coyote/AsyncStateMachine.java
index 1657840..d4b274e 100644
--- a/java/org/apache/coyote/AsyncStateMachine.java
+++ b/java/org/apache/coyote/AsyncStateMachine.java
@@ -31,108 +31,91 @@ import org.apache.tomcat.util.security.PrivilegedSetTccl;
* <pre>
* The internal states that are used are:
* DISPATCHED - Standard request. Not in Async mode.
- * STARTING - ServletRequest.startAsync() has been called but the
- * request in which that call was made has not finished
- * processing.
- * STARTED - ServletRequest.startAsync() has been called and the
- * request in which that call was made has finished
- * processing.
+ * STARTING - ServletRequest.startAsync() has been called from
+ * Servlet.service() but service() has not exited.
+ * STARTED - ServletRequest.startAsync() has been called from
+ * Servlet.service() and service() has exited.
* READ_WRITE_OP - Performing an asynchronous read or write.
* MUST_COMPLETE - ServletRequest.startAsync() followed by complete() have
* been called during a single Servlet.service() method. The
- * complete() will be processed as soon as the request
- * finishes.
- * COMPLETE_PENDING - ServletRequest.startAsync() has been called and before
the
- * request in which that call was had finished processing,
- * complete() was called for a non-container thread. The
- * complete() will be processed as soon as the request
- * finishes. This is different to MUST_COMPLETE because of
- * differences required to avoid race conditions during
error
- * handling.
+ * complete() will be processed as soon as Servlet.service()
+ * exits.
+ * COMPLETE_PENDING - ServletRequest.startAsync() has been called from
+ * Servlet.service() but, before service() exited,
complete()
+ * was called from another thread. The complete() will
+ * be processed as soon as Servlet.service() exits.
* COMPLETING - The call to complete() was made once the request was in
- * the STARTED state. May or may not be triggered by a
- * container thread - depends if start(Runnable) was used.
+ * the STARTED state.
* TIMING_OUT - The async request has timed out and is waiting for a call
- * to complete(). If that isn't made, the error state will
- * entered.
+ * to complete() or dispatch(). If that isn't made, the
error
+ * state will be entered.
* MUST_DISPATCH - ServletRequest.startAsync() followed by dispatch() have
* been called during a single Servlet.service() method. The
- * dispatch() will be processed as soon as the request
- * finishes.
- * DISPATCH_PENDING - ServletRequest.startAsync() has been called and before
the
- * request in which that call was had finished processing,
- * dispatch() was called for a non-container thread. The
- * dispatch() will be processed as soon as the request
- * finishes. This is different to MUST_DISPATCH because of
- * differences required to avoid race conditions during
error
- * handling.
+ * dispatch() will be processed as soon as Servlet.service()
+ * exits.
+ * DISPATCH_PENDING - ServletRequest.startAsync() has been called from
+ * Servlet.service() but, before service() exited,
dispatch()
+ * was called from another thread. The dispatch() will
+ * be processed as soon as Servlet.service() exits.
* DISPATCHING - The dispatch is being processed.
- * MUST_ERROR - ServletRequest.startAsync() has been called followed by
an
- * I/O error on a non-container thread. The main purpose of
- * this state is to prevent additional async actions
- * (complete(), dispatch() etc.) on the non-container
thread.
- * The container will perform the necessary error handling,
- * including ensuring that the AsyncLister.onError() method
- * is called.
+ * MUST_ERROR - ServletRequest.startAsync() has been called from
+ * Servlet.service() but, before service() exited, an I/O
+ * error occured on another thread. The container will
+ * perform the necessary error handling when
+ * Servlet.service() exits.
* ERROR - Something went wrong.
*
- *
|-----«-------------------------------«------------------------------|
- * |
|
- * | error()
|
- * |-----------------»---| |
|--«--------MUST_ERROR---------------«------------------------| |
- * | \|/ \|/\|/
| |
- * | |----------«-----E R R O
R--«-----------------------«-------------------------------| | |
- * | | complete() /|\/|\\ \-«--------------------------------«-------|
| | |
- * | | | | \ |
| | |
- * | | |-----»-------| | \-----------»----------| |
| | |
- * | | | | |dispatch() |
| ^ |
- * | | | | \|/ ^
| | |
- * | | | | |--|timeout() | |
| | |
- * | | | post() | | \|/ | post() |
| | |
- * | | | |---------- | --»DISPATCHED«---------- |
--------------COMPLETING«-----| | | |
- * | | | | | /|\/|\ | | | /|\
/|\ | | | |
- * | | | | |---»- | ---| | |startAsync() | timeout()|--|
| | | | |
- * | | ^ ^ | | | | |
| | ^ | |
- * | | | | | |-- \ -----| | complete() |
|post() | | | |
- * | | | | | | \ | /--»----- |
---COMPLETE_PENDING-»-| ^ | | |
- * | | | | | | \ | / |
| | | |
- * | | | | | ^ \ | / |
complete() | | | |
- * | \|/ | | | | \ \|/ / post() |
/---»-----| | ^ |
- * | MUST_COMPLETE-«- | - | --«----STARTING--»--------- | ------------| /
| | |
- * | /|\ /|\ | | complete() | \ | | /
error() | | ^
- * | | | | | | \ | |
//---»----------| | |
- * | | | ^ | dispatch()| \ | post() | //
| |
- * | | | | | | \ | |-----| | //
nct-io-error | |
- * | | | | | | \ | | | |
///---»---------------| |
- * | | | | | \|/ \ | | \|/\| |||
|
- * | | | | |--«--MUST_DISPATCH-----«-----|
|--«--STARTED«---------«---------| |
- * | | | | dispatched() /|\ | \ / | |
post() | |
- * | | | | | | \ / | |
| |
- * | | | | | | \ / | |
| |
- * | | | | | |post() | | | |
^ |
- * ^ | ^ | | | \|/ | |
|asyncOperation() | |
- * | | | ^ | | DISPATCH_PENDING | | |
| |
- * | | | | | | |post() | | |
| |
- * | | | | | | | |----------| |
|»-READ_WRITE_OP--»---| |
- * | | | | | | | | dispatch() |
| | | |
- * | | | | | | | | |
| | | |
- * | | | |post() | | | | timeout()|
| | | error()|
- * | | | |dispatched() | \|/\|/ \|/ |
dispatch()| | |-»--------|
- * | | | |---«---------- | ---DISPATCHING«-----«------ |
------«----| |
- * | | | | | /|\ |
|
- * | | | | |----| |
|
- * | | | | timeout() |
|
- * | | | | |
|
- * | | | | dispatch() \|/
|
- * | | | |-----------«-----------TIMING_OUT
|
- * | | | | |
|
- * | | |-------«----------------------------------«------| |
|
- * | | complete() |
|
- * | | |
|
- * |«- | ----«-------------------«-------------------------------«--|
|
- * | error()
|
- * | complete()
|
- *
|----------------------------------------------------------------------------|
+ *
+ * The valid state transitions are:
+ *
+ * post() dispatched()
+ * |-------»------------------»---------|
|-------«-----------------------«-----|
+ * | | |
|
+ * | | | post()
|
+ * | post() \|/ \|/ dispatched()
|
+ * |
|-----»----------------»DISPATCHED«-------------«-------------| |
+ * | | | /|\ |
| |
+ * | | startAsync()| |--|timeout()
| |
+ * ^ | |
| |
+ * | | complete() | dispatch()
^ |
+ * | | |--«---------------«-- | ---«--MUST_ERROR--»-----|
| |
+ * | | | | /|\ |
| |
+ * | ^ | | | |
| |
+ * | | | | /-----|error() |
| |
+ * | | | | / |
^ |
+ * | | \|/ ST-complete() \|/ / ST-dispatch() \|/
| |
+ * |
MUST_COMPLETE«--------«--------STARTING--------»---------»MUST_DISPATCH |
+ * | / | \
|
+ * | / | \
|
+ * | OT-complete() / | \ OT-dispatch()
|
+ * | COMPLETE_PENDING«------«------/ |
\-------»---------»DISPATCH_PENDING |
+ * | | | |
|
+ * | post()| timeout() post()| post() post()|
timeout() |
+ * | | |--| | |--| |
|--| |
+ * | \|/ \|/ | complete() \|/\|/ | dispatch() \|/
\|/ | |
+ *
|--«-----COMPLETING«--------«----------STARTED--------»---------»DISPATCHING----|
+ * /|\ /|\ /|\ | /|\ \ /|\ /|\
/|\
+ * | | | | \ \asyncOperation() | |
|
+ * | | | timeout()| \ \ | |
|
+ * | | | | \ \ | |
|
+ * | | | | \ \ | |
|
+ * | | | | \ \ | |
|
+ * | | | | \ \ | |
|
+ * | | | | post()\ \ dispatch()| |
|
+ * | | | complete() | \ \|/ | |
|
+ * | | |---«------------«-- | --«---READ_WRITE----»----| |
|
+ * | | | |
|
+ * | | complete() \|/ dispatch() |
|
+ * | |------------«-------TIMING_OUT--------»----------------|
|
+ * |
|
+ * | complete() dispatch()
|
+ *
|---------------«-----------ERROR--------------»-----------------|
+ *
+ *
+ * Notes: * For clarity, the transitions to ERROR which are valid from every
state apart from
+ * STARTING are not shown.
+ * * All transitions may happen on either the Servlet.service() thread
(ST) or on any
+ * other thread (OT) unless explicitly marked.
* </pre>
*/
public class AsyncStateMachine {
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]