-
Ozan Tezcan authored
Added a pool for temporary client objects to reuse in module operations. By reusing temporary clients, we are avoiding expensive createClient()/freeClient() calls and improving performance of RM_BlockClient() and RM_GetThreadSafeContext() calls. This commit contains two optimizations: 1 - RM_BlockClient() and RM_GetThreadSafeContext() calls create temporary clients and they are freed in RM_UnblockClient() and RM_FreeThreadSafeContext() calls respectively. Creating/destroying client object takes quite time. To avoid that, added a pool of temporary clients. Pool expands when more clients are needed. Also, added a cron function to shrink the pool and free unused clients after some time. Pool starts with zero clients in it. It does not have max size and can grow unbounded as we need it. We will keep minimum of 8 temporary clients in the pool once created. Keeping small amount of clients to avoid client allocation costs if temporary clients are required after some idle period. 2 - After unblocking a client (RM_UnblockClient()), one byte is written to pipe to wake up Redis main thread. If there are many clients that will be unblocked, each operation requires one write() call which is quite expensive. Changed code to avoid subsequent calls if possible. There are a few more places that need temporary client objects (e.g RM_Call()). These are now using the same temporary client pool to make things more centralized.
6790d848