res_pjsip.c: Make taskprocessor scheduling algorithm pick the shortest queue
authorAlexei Gradinari <alex2grad@gmail.com>
Mon, 5 Nov 2018 18:44:28 +0000 (13:44 -0500)
committerAlexei Gradinari <alex2grad@gmail.com>
Tue, 6 Nov 2018 15:26:11 +0000 (10:26 -0500)
The current round-robin method does not take the current taskprocessor
load into consideration when distributing requests.  Using the least-size
method the request goes to the taskprocessor that is servicing the least
number of active tasks at the current time.

Longer running tasks with the round-robin method can delay processing
tasks.

* Change the algorithm from round-robin to least-size for picking the
PJSIP taskprocessor from the default serializer pool.

Change-Id: I7b8d8cc2c2490494f579374b6af0a4868e3a37cd

res/res_pjsip.c

index 3391fee..58645b6 100644 (file)
 /*! Number of serializers in pool if one not supplied. */
 #define SERIALIZER_POOL_SIZE           8
 
-/*! Next serializer pool index to use. */
-static int serializer_pool_pos;
-
 /*! Pool of serializers to use if not supplied. */
 static struct ast_taskprocessor *serializer_pool[SERIALIZER_POOL_SIZE];
 
@@ -4634,22 +4631,20 @@ static int serializer_pool_setup(void)
 
 static struct ast_taskprocessor *serializer_pool_pick(void)
 {
-       struct ast_taskprocessor *serializer;
+       int idx;
+       int pos = 0;
 
-       unsigned int pos;
+       if (!serializer_pool[0]) {
+               return NULL;
+       }
 
-       /*
-        * Pick a serializer to use from the pool.
-        *
-        * Note: We don't care about any reentrancy behavior
-        * when incrementing serializer_pool_pos.  If it gets
-        * incorrectly incremented it doesn't matter.
-        */
-       pos = serializer_pool_pos++;
-       pos %= SERIALIZER_POOL_SIZE;
-       serializer = serializer_pool[pos];
+       for (idx = 1; idx < SERIALIZER_POOL_SIZE; ++idx) {
+               if (ast_taskprocessor_size(serializer_pool[idx]) < ast_taskprocessor_size(serializer_pool[pos])) {
+                       pos = idx;
+               }
+       }
 
-       return serializer;
+       return serializer_pool[pos];
 }
 
 int ast_sip_push_task(struct ast_taskprocessor *serializer, int (*sip_task)(void *), void *task_data)