<html xmlns:v="urn:schemas-microsoft-com:vml" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:w="urn:schemas-microsoft-com:office:word" xmlns:m="http://schemas.microsoft.com/office/2004/12/omml" xmlns="http://www.w3.org/TR/REC-html40">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=koi8-r">
<meta name="Generator" content="Microsoft Word 15 (filtered medium)">
<style><!--
/* Font Definitions */
@font-face
        {font-family:"Cambria Math";
        panose-1:2 4 5 3 5 4 6 3 2 4;}
@font-face
        {font-family:Calibri;
        panose-1:2 15 5 2 2 2 4 3 2 4;}
@font-face
        {font-family:Consolas;
        panose-1:2 11 6 9 2 2 4 3 2 4;}
/* Style Definitions */
p.MsoNormal, li.MsoNormal, div.MsoNormal
        {margin:0in;
        font-size:11.0pt;
        font-family:"Calibri",sans-serif;
        mso-ligatures:standardcontextual;}
a:link, span.MsoHyperlink
        {mso-style-priority:99;
        color:#0563C1;
        text-decoration:underline;}
p.MsoListParagraph, li.MsoListParagraph, div.MsoListParagraph
        {mso-style-priority:34;
        margin-top:0in;
        margin-right:0in;
        margin-bottom:0in;
        margin-left:.5in;
        font-size:11.0pt;
        font-family:"Calibri",sans-serif;
        mso-ligatures:standardcontextual;}
span.EmailStyle17
        {mso-style-type:personal-compose;
        font-family:"Calibri",sans-serif;
        color:windowtext;}
.MsoChpDefault
        {mso-style-type:export-only;}
@page WordSection1
        {size:8.5in 11.0in;
        margin:1.0in 1.0in 1.0in 1.0in;}
div.WordSection1
        {page:WordSection1;}
/* List Definitions */
@list l0
        {mso-list-id:151877863;
        mso-list-type:hybrid;
        mso-list-template-ids:1159745606 -47515864 67698713 67698715 67698703 67698713 67698715 67698703 67698713 67698715;}
@list l0:level1
        {mso-level-number-format:alpha-lower;
        mso-level-text:"%1\)";
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:.75in;
        text-indent:-.25in;}
@list l0:level2
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:1.25in;
        text-indent:-.25in;}
@list l0:level3
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        margin-left:1.75in;
        text-indent:-9.0pt;}
@list l0:level4
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:2.25in;
        text-indent:-.25in;}
@list l0:level5
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:2.75in;
        text-indent:-.25in;}
@list l0:level6
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        margin-left:3.25in;
        text-indent:-9.0pt;}
@list l0:level7
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:3.75in;
        text-indent:-.25in;}
@list l0:level8
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:4.25in;
        text-indent:-.25in;}
@list l0:level9
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        margin-left:4.75in;
        text-indent:-9.0pt;}
@list l1
        {mso-list-id:1032731957;
        mso-list-type:hybrid;
        mso-list-template-ids:611251286 -1114587110 67698713 67698715 67698703 67698713 67698715 67698703 67698713 67698715;}
@list l1:level1
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:.75in;
        text-indent:-.25in;}
@list l1:level2
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:1.25in;
        text-indent:-.25in;}
@list l1:level3
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        margin-left:1.75in;
        text-indent:-9.0pt;}
@list l1:level4
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:2.25in;
        text-indent:-.25in;}
@list l1:level5
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:2.75in;
        text-indent:-.25in;}
@list l1:level6
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        margin-left:3.25in;
        text-indent:-9.0pt;}
@list l1:level7
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:3.75in;
        text-indent:-.25in;}
@list l1:level8
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        margin-left:4.25in;
        text-indent:-.25in;}
@list l1:level9
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        margin-left:4.75in;
        text-indent:-9.0pt;}
@list l2
        {mso-list-id:1141731513;
        mso-list-type:hybrid;
        mso-list-template-ids:27537540 67698703 67698713 67698715 67698703 67698713 67698715 67698703 67698713 67698715;}
@list l2:level1
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        text-indent:-.25in;}
@list l2:level2
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        text-indent:-.25in;}
@list l2:level3
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        text-indent:-9.0pt;}
@list l2:level4
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        text-indent:-.25in;}
@list l2:level5
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        text-indent:-.25in;}
@list l2:level6
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        text-indent:-9.0pt;}
@list l2:level7
        {mso-level-tab-stop:none;
        mso-level-number-position:left;
        text-indent:-.25in;}
@list l2:level8
        {mso-level-number-format:alpha-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:left;
        text-indent:-.25in;}
@list l2:level9
        {mso-level-number-format:roman-lower;
        mso-level-tab-stop:none;
        mso-level-number-position:right;
        text-indent:-9.0pt;}
ol
        {margin-bottom:0in;}
ul
        {margin-bottom:0in;}
--></style><!--[if gte mso 9]><xml>
<o:shapedefaults v:ext="edit" spidmax="1026" />
</xml><![endif]--><!--[if gte mso 9]><xml>
<o:shapelayout v:ext="edit">
<o:idmap v:ext="edit" data="1" />
</o:shapelayout></xml><![endif]-->
</head>
<body lang="EN-US" link="#0563C1" vlink="#954F72" style="word-wrap:break-word">
<div class="WordSection1">
<p class="MsoNormal">Hello All, <o:p></o:p></p>
<p class="MsoNormal"><o:p> </o:p></p>
<p class="MsoNormal">This previous <a href="https://lists.ozlabs.org/pipermail/openbmc/2023-May/033495.html">
thread</a> captures the motive behind our interest in chasing multi-threaded solution for bmcweb.
<o:p></o:p></p>
<p class="MsoNormal">Thanks to Ed for putting up this initial patch. <a href="https://gerrit.openbmc.org/c/openbmc/bmcweb/+/63710">
https://gerrit.openbmc.org/c/openbmc/bmcweb/+/63710</a><o:p></o:p></p>
<p class="MsoNormal"><o:p> </o:p></p>
<p class="MsoNormal">We have been testing this patch in the recent times and I wanted to put a summary of our observations.  <o:p></o:p></p>
<p class="MsoNormal"><o:p> </o:p></p>
<ol style="margin-top:0in" start="1" type="1">
<li class="MsoListParagraph" style="margin-left:0in;mso-list:l2 level1 lfo1">The original patch was not creating any explicit threads and we did not find boost::asio creating them for us.
<o:p></o:p></li></ol>
<p class="MsoListParagraph">So as per this <a href="https://theboostcpplibraries.com/boost.asio-scalability">
article</a> from boost I modified the patch to create a thread pool and share the same IO context among all threads.  <o:p></o:p></p>
<p class="MsoListParagraph">When I tested this change, I found two problems. <o:p>
</o:p></p>
<ol style="margin-top:0in" start="1" type="a">
<li class="MsoListParagraph" style="margin-left:.25in;mso-list:l0 level1 lfo2">Sharing same IO context between multiple threads does not work.
<o:p></o:p></li></ol>
<p class="MsoListParagraph" style="margin-left:.75in">I have logged this issue  <a href="https://github.com/chriskohlhoff/asio/issues/1353">https://github.com/chriskohlhoff/asio/issues/1353</a>  in boost::asio git hub page with sample code to reproduce the
 issue. <o:p></o:p></p>
<p class="MsoListParagraph" style="margin-left:.75in">It would be great if someone else test this sample code and share the results based on their platform.
<o:p></o:p></p>
<ol style="margin-top:0in" start="2" type="a">
<li class="MsoListParagraph" style="margin-left:.25in;mso-list:l0 level1 lfo2">Sharing dbus connection across threads is not safe:
<o:p></o:p></li></ol>
<p class="MsoNormal" style="margin-left:.75in">when we share same IO context between multiple threads, it’s possible that the async job posted by one thread, can be picked up by some other thread.
<o:p></o:p></p>
<p class="MsoNormal" style="margin-left:.75in">If thread1 makes crow::connections::systemBus().async_method_call then the response lambda can get executed in thead2’s context.
<o:p></o:p></p>
<p class="MsoNormal" style="margin-left:.75in">When thread2 is trying to read from the dbus connection, thread1 can make a new request on the same bus connection as part of handling another URI request.
<o:p></o:p></p>
<p class="MsoNormal" style="margin-left:.75in">Sdbus is not thread safe when connection object is shared between multiple threads which can perform read/write operations.  <o:p></o:p></p>
<p class="MsoListParagraph" style="margin-left:.75in"><o:p> </o:p></p>
<ol style="margin-top:0in" start="2" type="1">
<li class="MsoListParagraph" style="margin-left:0in;mso-list:l2 level1 lfo1">IO Context per thread.
<o:p></o:p></li></ol>
<p class="MsoListParagraph">Since sharing IO context was not working I took the second approach mentioned in this
<a href="https://theboostcpplibraries.com/boost.asio-scalability">article</a> which is to dedicate IO context per threads.
<o:p></o:p></p>
<p class="MsoListParagraph">Major design challenge with this approach is to decide which jobs must be executed in which IO context.<o:p></o:p></p>
<p class="MsoListParagraph">I started with dedicating one thread/IO context to manage all the incoming requests and handling responses back to the clients.
<o:p></o:p></p>
<p class="MsoListParagraph">I dedicated another thread/IO context to only manage aggregate URIs which have 1K+ sensors response (MRDs) to populate and does not have tighter latency requirements.
<o:p></o:p></p>
<p class="MsoListParagraph">Our goal is to have faster response on the power/thermal URIs which is served by the main thread and is not blocked by huge response handling required by aggregate URIs which is managed by the secondary thread.<o:p></o:p></p>
<p class="MsoListParagraph">From our previous performance experiments, we had found that JSON response preparation for 5K+ sensors was taking around 250 to 300ms in bmcweb during which power/thermals URIs were blocked.  <o:p></o:p></p>
<p class="MsoListParagraph"><o:p> </o:p></p>
<p class="MsoListParagraph">     ‚€€€€€€€€€€ƒ          ‚€€€€€€€€€€€€€€€€€€ƒ<o:p></o:p></p>
<p class="MsoListParagraph">     MainThread          MRD_Handler_Thread<o:p></o:p></p>
<p class="MsoListParagraph">     „€€€€<span style="font-family:"Arial",sans-serif">ˆ</span>€€€€€…          „€€€€€€€€<span style="font-family:"Arial",sans-serif">ˆ</span>€€€€€€€€€…<o:p></o:p></p>
<p class="MsoListParagraph">                   asio::post(request)                 
<o:p></o:p></p>
<p class="MsoListParagraph">                 €€€€€€€€€€€€€€€€€€€>          <o:p>
</o:p></p>
<p class="MsoListParagraph">                                                                     
<o:p></o:p></p>
<p class="MsoListParagraph">                   asio::post(response)              
<o:p></o:p></p>
<p class="MsoListParagraph">                 <€€€€€€€€€€€€€€€€€€€     <o:p></o:p></p>
<p class="MsoListParagraph">     ‚€€€€<span style="font-family:"Arial",sans-serif">‰</span>€€€€€ƒ          ‚€€€€€€€€<span style="font-family:"Arial",sans-serif">‰</span>€€€€€€€€€ƒ<o:p></o:p></p>
<p class="MsoListParagraph">     MainThread          MRD_Handler_Thread<o:p></o:p></p>
<p class="MsoListParagraph">     „€€€€€€€€€€…          „€€€€€€€€€€€€€€€€€€… <o:p>
</o:p></p>
<p class="MsoListParagraph"> <o:p></o:p></p>
<p class="MsoListParagraph">Based on the URI main thread decides to continue to process the request or offload it to the MRD handler thread.
<o:p></o:p></p>
<p class="MsoListParagraph">The response received from the MRD thread is returned to the client by the main thread.
<o:p></o:p></p>
<p class="MsoNormal">               The performance results with the solution are great. We see almost 50% improvement in the performance of power/thermal URIs.
<o:p></o:p></p>
<p class="MsoNormal">               Here is performance is measured based on worst case latency seen on power thermal URIs when there are concurrent clients accessing power/thermal + MRD URIs.
<o:p></o:p></p>
<p class="MsoNormal">               <o:p></o:p></p>
<p class="MsoNormal">               However, this solution seems to have some stability issues in the overnight long run tests.
<o:p></o:p></p>
<p class="MsoNormal" style="text-indent:.5in">The crash is seen around boost:post APIs in multi-threading context. I have logged a different bug in boost::asio to demonstrate this problem.
<a href="https://github.com/chriskohlhoff/asio/issues/1352">https://github.com/chriskohlhoff/asio/issues/1352</a><o:p></o:p></p>
<p class="MsoNormal" style="text-indent:.5in">I will follow up to check if boost can help us with this fix.
<o:p></o:p></p>
<p class="MsoNormal"><o:p> </o:p></p>
<p class="MsoNormal">What I am looking for <o:p></o:p></p>
<ol style="margin-top:0in" start="1" type="1">
<li class="MsoListParagraph" style="margin-left:.25in;mso-list:l1 level1 lfo3">Does anyone have any different proposal for sharing IO context between threads which can work our bmc platform?
<o:p></o:p></li><li class="MsoListParagraph" style="margin-left:.25in;mso-list:l1 level1 lfo3">Feedback on handling dbus connection between multiple threads in the context of bmcweb?<o:p></o:p></li><li class="MsoListParagraph" style="margin-left:.25in;mso-list:l1 level1 lfo3">Is this a good model to dedicate threads based on the use case as we are not able to make IO sharing between threads work well?<o:p></o:p></li><li class="MsoListParagraph" style="margin-left:.25in;mso-list:l1 level1 lfo3">Any better way to Post asio jobs across threads and make it stable?<o:p></o:p></li></ol>
<p class="MsoNormal"><o:p> </o:p></p>
<p class="MsoNormal">Thanks <o:p></o:p></p>
<p class="MsoNormal">Rohit PAI <o:p></o:p></p>
<p class="MsoNormal"><o:p> </o:p></p>
</div>
</body>
</html>