Re: [Cppcms-users] Synchronous app calls io_service.post() and blocks itself
Brought to you by:
artyom-beilis
|
From: CN <cn...@fa...> - 2014-03-18 12:01:04
|
Thank you for your kind reminder! I think I get your points.
> > Such hand made "cache" seems to be unable to fit my case. I
> > need to use
> > booster::aio::io_service as a synchronizer, like a mutex, to
> >
> > *sequentially* execute cppdb operations and manipulate
> > in-memory data.
>
> One VERY important point to alarm you.
>
> There is ONE even loop that handles LOTS of operations:
> incoming connections, uploads, transfers, request parsing,
> etc.
>
> It MUST not be blocked. As it basically blocks the entire CppCMS
> service from doing its job.
>
> If you call some heavy query to cppdb FROM the event loop
> or async app. You'll block the entire application.
>
> It is bad idea to abuse the even loop for such a purpose.
> Any operations in the async application or event loop must
> be as fast as possible and what is important - never block.
>
> If you run for example an SQL query that access the disk
> you may delay your entire cppcms application up to 6ms
> required for a physical disk to seek to the non-cached data.
>
> If you need to perform blocking/heavy operation by the async-app,
> inside event loop - post it to the thread pool and get the
> results "posted" back.
I have two questions if I opt for this approach:
(1) Can I simply use
cppcms::thread_pool &thread_pool()
in the central service or must I create my own instance of
cppcms::thread_pool?
(2) Synchronous applications require below technique you mentioned
earlier, or std::future or the likes, to get the results "posted" back
by the jobs running in thread pool. Correct?
**begin technique**
technically you can implement this by for example waiting for a
conditional variable.
that would be changed in the event loop:
Caller
------------------
this->resp_is_ready=false
async_app->service().get_io_service().post(boost::bind(&my_class::my_method,this));
while(true){
booster::unique_lock guard(this->resp_is_ready_mutex)
this->resp_is_ready_cond.wait(guard)
if(this->resp_is_ready)
break;
}
-------------
Handler
-------------
my_class:my_method()
{
// do something with async app/withing the event loop
booster::unique_lock guard(this->resp_is_ready_mutex);
this->resp_is_ready = true
this->resp_is_ready_cond.notify_one()
}
**end technique**
> If you want some "job queue" for sequential execution you'll probably
> want to
> create some additional execution queue,
>
> you may create your own booster::aio::io_service and run it in its own
> thread
> that would act like a dispatch queue (although it is most likely
> overkill)
>
> Or write your own simple job queue (which is quite a textbook tasks)
Regards,
CN
--
http://www.fastmail.fm - Accessible with your email software
or over the web
|