This is an automated email from the ASF dual-hosted git repository.

zwoop pushed a commit to branch 9.0.x
in repository https://gitbox.apache.org/repos/asf/trafficserver.git


The following commit(s) were added to refs/heads/9.0.x by this push:
     new bc0ebcb  Ensure TSContSchedule API family are called from an EThread.
bc0ebcb is described below

commit bc0ebcbaebf1db107b65102c07efe93d14a57312
Author: Sudheer Vinukonda <[email protected]>
AuthorDate: Thu Mar 26 12:53:33 2020 -0700

    Ensure TSContSchedule API family are called from an EThread.
    
    If called from a non-EThread, the Mutex_Lock ends up not acquiring
    the lock but still releasing it causing weird behavior much later
    
    (cherry picked from commit 7ff627fdc495cdfec109919bcf13c9c261a9783e)
---
 doc/developer-guide/api/functions/TSContSchedule.en.rst      |  3 +++
 .../api/functions/TSContScheduleOnPool.en.rst                |  3 +++
 .../api/functions/TSContScheduleOnThread.en.rst              |  3 +++
 src/traffic_server/InkAPI.cc                                 | 12 ++++++++++++
 4 files changed, 21 insertions(+)

diff --git a/doc/developer-guide/api/functions/TSContSchedule.en.rst 
b/doc/developer-guide/api/functions/TSContSchedule.en.rst
index 8984174..26d8228 100644
--- a/doc/developer-guide/api/functions/TSContSchedule.en.rst
+++ b/doc/developer-guide/api/functions/TSContSchedule.en.rst
@@ -44,6 +44,9 @@ another thread this can be problematic to be correctly timed. 
The return value c
 :func:`TSActionDone` to see if the continuation ran before the return, which 
is possible if
 :arg:`timeout` is `0`. Returns ``nullptr`` if thread affinity was cleared.
 
+Note that the TSContSchedule() family of API shall only be called from an ATS 
EThread.
+Calling it from raw non-EThreads can result in unpredictable behavior.
+
 See Also
 ========
 
diff --git a/doc/developer-guide/api/functions/TSContScheduleOnPool.en.rst 
b/doc/developer-guide/api/functions/TSContScheduleOnPool.en.rst
index 6ba03cf..d14b57f 100644
--- a/doc/developer-guide/api/functions/TSContScheduleOnPool.en.rst
+++ b/doc/developer-guide/api/functions/TSContScheduleOnPool.en.rst
@@ -54,6 +54,9 @@ called and continuations that use them have the same 
restrictions. ``TS_THREAD_P
 are threads that exist to perform long or blocking actions, although 
sufficiently long operation can
 impact system performance by blocking other continuations on the threads.
 
+Note that the TSContSchedule() family of API shall only be called from an ATS 
EThread.
+Calling it from raw non-EThreads can result in unpredictable behavior.
+
 Example Scenarios
 =================
 
diff --git a/doc/developer-guide/api/functions/TSContScheduleOnThread.en.rst 
b/doc/developer-guide/api/functions/TSContScheduleOnThread.en.rst
index 5e196f9..27c48bf 100644
--- a/doc/developer-guide/api/functions/TSContScheduleOnThread.en.rst
+++ b/doc/developer-guide/api/functions/TSContScheduleOnThread.en.rst
@@ -35,6 +35,9 @@ Description
 
 Mostly the same as :func:`TSContSchedule`. Schedules :arg:`contp` on 
:arg:`ethread`.
 
+Note that the TSContSchedule() family of API shall only be called from an ATS 
EThread.
+Calling it from raw non-EThreads can result in unpredictable behavior.
+
 See Also
 ========
 
diff --git a/src/traffic_server/InkAPI.cc b/src/traffic_server/InkAPI.cc
index e9a754a..cc500ed 100644
--- a/src/traffic_server/InkAPI.cc
+++ b/src/traffic_server/InkAPI.cc
@@ -4516,6 +4516,9 @@ TSContSchedule(TSCont contp, TSHRTime timeout)
 {
   sdk_assert(sdk_sanity_check_iocore_structure(contp) == TS_SUCCESS);
 
+  /* ensure we are on a EThread */
+  sdk_assert(sdk_sanity_check_null_ptr((void *)this_ethread()) == TS_SUCCESS);
+
   FORCE_PLUGIN_SCOPED_MUTEX(contp);
 
   INKContInternal *i = reinterpret_cast<INKContInternal *>(contp);
@@ -4547,6 +4550,9 @@ TSContScheduleOnPool(TSCont contp, TSHRTime timeout, 
TSThreadPool tp)
 {
   sdk_assert(sdk_sanity_check_iocore_structure(contp) == TS_SUCCESS);
 
+  /* ensure we are on a EThread */
+  sdk_assert(sdk_sanity_check_null_ptr((void *)this_ethread()) == TS_SUCCESS);
+
   FORCE_PLUGIN_SCOPED_MUTEX(contp);
 
   INKContInternal *i = reinterpret_cast<INKContInternal *>(contp);
@@ -4624,6 +4630,9 @@ TSContScheduleEvery(TSCont contp, TSHRTime every /* 
millisecs */)
 {
   sdk_assert(sdk_sanity_check_iocore_structure(contp) == TS_SUCCESS);
 
+  /* ensure we are on a EThread */
+  sdk_assert(sdk_sanity_check_null_ptr((void *)this_ethread()) == TS_SUCCESS);
+
   FORCE_PLUGIN_SCOPED_MUTEX(contp);
 
   INKContInternal *i = reinterpret_cast<INKContInternal *>(contp);
@@ -4650,6 +4659,9 @@ TSContScheduleEveryOnPool(TSCont contp, TSHRTime every, 
TSThreadPool tp)
 {
   sdk_assert(sdk_sanity_check_iocore_structure(contp) == TS_SUCCESS);
 
+  /* ensure we are on a EThread */
+  sdk_assert(sdk_sanity_check_null_ptr((void *)this_ethread()) == TS_SUCCESS);
+
   FORCE_PLUGIN_SCOPED_MUTEX(contp);
 
   INKContInternal *i = reinterpret_cast<INKContInternal *>(contp);

Reply via email to