{"id":8513,"date":"2012-01-18T07:00:00","date_gmt":"2012-01-18T07:00:00","guid":{"rendered":"https:\/\/blogs.msdn.microsoft.com\/oldnewthing\/2012\/01\/18\/dont-try-to-allocate-memory-until-there-is-only-x-free\/"},"modified":"2012-01-18T07:00:00","modified_gmt":"2012-01-18T07:00:00","slug":"dont-try-to-allocate-memory-until-there-is-only-x-free","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/oldnewthing\/20120118-00\/?p=8513","title":{"rendered":"Don&#039;t try to allocate memory until there is only x% free"},"content":{"rendered":"<p>I have an ongoing conflict with my in-laws. Their concept of the correct amount of food to have in the refrigerator is &#8220;more than will comfortably fit.&#8221; Whenever they come to visit (which is quite often), they make sure to bring enough food so that my refrigerator bursts at the seams, with vegetables and eggs and other foodstuffs crammed into every available nook and cranny. If I&#8217;m lucky, the amount of food manages to get down to &#8220;only slightly overfull&#8221; before their next visit. And the problem isn&#8217;t restricted to the refrigerator. I once cleared out some space in the garage, only to find that they decided to use that space to store <i>more food<\/i>. (Who knows, maybe one day I will return from an errand to find that my parking space has been filled with <i>still more food<\/i> while I was gone.)\n Occasionally, a customer will ask for a way to design their program so it continues consuming RAM until there is only x% free. The idea is that their program should use RAM aggressively, while still leaving enough RAM available (x%) for other use. Unless you are designing a system where you are the only program running on the computer, this is a bad idea.\n Consider what happens if two programs try to be &#8220;good programs&#8221; and leave x% of RAM available for other purposes. Let&#8217;s call the programs Program&nbsp;10 (which wants to keep 10% of the RAM free) Program&nbsp;20 (which wants to keep 20% of the RAM free). For simplicity, let&#8217;s suppose that they are the only two programs on the system.\n Initially, the computer is not under memory pressure, so both programs can allocate all the memory they want without any hassle. But as time passes, the amount of free memory slowly decreases.<\/p>\n<table border=\"1\" cellpadding=\"3\" style=\"border-collapse: collapse;width: 80%;text-align: center\">\n<tr>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (20%)<\/td>\n<td colspan=\"60\" style=\"width: 60%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (60%)<\/td>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (20%)<\/td>\n<\/tr>\n<tr>\n<td colspan=\"30\" style=\"width: 30%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (30%)<\/td>\n<td colspan=\"40\" style=\"width: 40%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (40%)<\/td>\n<td colspan=\"30\" style=\"width: 30%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (30%)<\/td>\n<\/tr>\n<tr>\n<td colspan=\"40\" style=\"width: 40%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (40%)<\/td>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (20%)<\/td>\n<td colspan=\"40\" style=\"width: 40%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (40%)<\/td>\n<\/tr>\n<\/table>\n<p> And then we hit a critical point: The amount of free memory drops below 20%.<\/p>\n<table border=\"1\" cellpadding=\"3\" style=\"border-collapse: collapse;width: 80%;text-align: center\">\n<tr>\n<td colspan=\"41\" style=\"width: 41%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (41%)<\/td>\n<td colspan=\"18\" style=\"width: 18%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (18%)<\/td>\n<td colspan=\"41\" style=\"width: 41%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (41%)<\/td>\n<\/tr>\n<\/table>\n<p> At this point, Program&nbsp;20 backs off in order to restore the amount of free memory back to 20%.<\/p>\n<table border=\"1\" cellpadding=\"3\" style=\"border-collapse: collapse;width: 80%;text-align: center\">\n<tr>\n<td colspan=\"41\" style=\"width: 41%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (41%)<\/td>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (20%)<\/td>\n<td colspan=\"39\" style=\"width: 39%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (39%)<\/td>\n<\/tr>\n<\/table>\n<p> Now, each time Program&nbsp;10 and Program&nbsp;20 think about allocating more memory, Program&nbsp;20 will say &#8220;Nope, I can&#8217;t do that because it would send the amount of free memory below 20%.&#8221; On the other hand, Program&nbsp;10 will happily allocate some more memory since it sees that there&#8217;s a whole 10% it can allocate before it needs to stop. And as soon as Program&nbsp;10 allocates that memory, Program&nbsp;20 will free some memory to bring the amount of free memory back up to 20%.<\/p>\n<table border=\"1\" cellpadding=\"3\" style=\"border-collapse: collapse;width: 80%;text-align: center\">\n<tr>\n<td colspan=\"42\" style=\"width: 42%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (42%)<\/td>\n<td colspan=\"19\" style=\"width: 19%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (19%)<\/td>\n<td colspan=\"39\" style=\"width: 39%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (39%)<\/td>\n<\/tr>\n<tr>\n<td colspan=\"42\" style=\"width: 42%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (42%)<\/td>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (20%)<\/td>\n<td colspan=\"38\" style=\"width: 38%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (38%)<\/td>\n<\/tr>\n<tr>\n<td colspan=\"43\" style=\"width: 43%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (43%)<\/td>\n<td colspan=\"19\" style=\"width: 19%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (19%)<\/td>\n<td colspan=\"38\" style=\"width: 38%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (38%)<\/td>\n<\/tr>\n<tr>\n<td colspan=\"43\" style=\"width: 43%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (43%)<\/td>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (20%)<\/td>\n<td colspan=\"37\" style=\"width: 37%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (37%)<\/td>\n<\/tr>\n<tr>\n<td colspan=\"44\" style=\"width: 44%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (44%)<\/td>\n<td colspan=\"19\" style=\"width: 19%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (19%)<\/td>\n<td colspan=\"37\" style=\"width: 37%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (37%)<\/td>\n<\/tr>\n<tr>\n<td colspan=\"44\" style=\"width: 44%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (44%)<\/td>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (20%)<\/td>\n<td colspan=\"36\" style=\"width: 36%\" bgcolor=\"#C0FFFF\" nowrap>     <b>Program&nbsp;20<\/b> (36%)<\/td>\n<\/tr>\n<\/table>\n<p> I think you see where this is going. Each time Program&nbsp;10 allocates a little more memory, Program&nbsp;20 frees the same amount of memory in order to get the total free memory back up to 20%. Eventually, we reach a situation like this:<\/p>\n<table border=\"1\" cellpadding=\"3\" style=\"border-collapse: collapse;width: 80%;text-align: center\">\n<tr>\n<td colspan=\"75\" style=\"width: 75%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (75%)<\/td>\n<td colspan=\"20\" style=\"width: 20%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (20%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<\/table>\n<p> Program&nbsp;20 is now curled up in the corner of the computer in a fetal position. Program&nbsp;10 meanwhile continues allocating memory, and Program&nbsp;20, having shrunk as much as it can, is forced to just sit there and whimper.<\/p>\n<table border=\"1\" cellpadding=\"3\" style=\"border-collapse: collapse;width: 80%;text-align: center\">\n<tr>\n<td colspan=\"76\" style=\"width: 76%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (76%)<\/td>\n<td colspan=\"19\" style=\"width: 19%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (19%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"77\" style=\"width: 77%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (77%)<\/td>\n<td colspan=\"18\" style=\"width: 18%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (18%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"78\" style=\"width: 78%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (78%)<\/td>\n<td colspan=\"17\" style=\"width: 17%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (17%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"79\" style=\"width: 79%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (79%)<\/td>\n<td colspan=\"16\" style=\"width: 16%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (16%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"80\" style=\"width: 80%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (80%)<\/td>\n<td colspan=\"15\" style=\"width: 15%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (15%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"81\" style=\"width: 81%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (81%)<\/td>\n<td colspan=\"14\" style=\"width: 14%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (14%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"82\" style=\"width: 82%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (82%)<\/td>\n<td colspan=\"13\" style=\"width: 13%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (13%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"83\" style=\"width: 83%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (83%)<\/td>\n<td colspan=\"12\" style=\"width: 12%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (12%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"84\" style=\"width: 84%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (84%)<\/td>\n<td colspan=\"11\" style=\"width: 11%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (11%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<tr>\n<td colspan=\"85\" style=\"width: 85%\" bgcolor=\"#FFC0FF\" nowrap>     <b>Program&nbsp;10<\/b> (85%)<\/td>\n<td colspan=\"10\" style=\"width: 10%\" bgcolor=\"#C0C0C0\" nowrap>     <b>Free<\/b> (10%)<\/td>\n<td colspan=\"5\" style=\"width: 5%\" bgcolor=\"#C0FFFF\" nowrap>     <font size=\"-2\"><b>P20<\/b> (5%)<\/font><\/td>\n<\/tr>\n<\/table>\n<p> Finally, Program&nbsp;10 stops allocating memory since it has reached its own personal limit of not allocating the last 10% of the computer&#8217;s RAM. But it&#8217;s too little too late. Program&nbsp;20 has already been forced into the corner, thrashing its brains out trying to survive on only 5% of the computer&#8217;s memory.<\/p>\n<p> It&#8217;s sort of like when people from two different cultures with different concepts of <i>personal space<\/i> have a face-to-face conversation. The person from the not-so-close culture will try to back away in order to preserve the necessary distance, while the person from the closer-is-better culture will move forward in order to close the gap. Eventually, the person from the not-so-close culture will end up with his back against the wall anxiously looking for an escape route. <\/p>\n","protected":false},"excerpt":{"rendered":"<p>I have an ongoing conflict with my in-laws. Their concept of the correct amount of food to have in the refrigerator is &#8220;more than will comfortably fit.&#8221; Whenever they come to visit (which is quite often), they make sure to bring enough food so that my refrigerator bursts at the seams, with vegetables and eggs [&hellip;]<\/p>\n","protected":false},"author":1069,"featured_media":111744,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[25],"class_list":["post-8513","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-oldnewthing","tag-code"],"acf":[],"blog_post_summary":"<p>I have an ongoing conflict with my in-laws. Their concept of the correct amount of food to have in the refrigerator is &#8220;more than will comfortably fit.&#8221; Whenever they come to visit (which is quite often), they make sure to bring enough food so that my refrigerator bursts at the seams, with vegetables and eggs [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/8513","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/users\/1069"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/comments?post=8513"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/8513\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/media\/111744"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/media?parent=8513"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/categories?post=8513"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/tags?post=8513"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}