<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>ServerAdmins.NET &#187; XCache Xcache.ini php optimization tuning opcode</title>
	<atom:link href="http://serveradmins.net/tag/xcache-xcacheini-php-optimization-tuning-opcode/feed/" rel="self" type="application/rss+xml" />
	<link>http://serveradmins.net</link>
	<description>Stuff for Server Admins...</description>
	<lastBuildDate>Fri, 09 Jul 2010 16:46:09 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0.1</generator>
		<item>
		<title>XCache Tuning for Optimized PHP on Linux</title>
		<link>http://serveradmins.net/tuning-xcache-for-fun-and-profit/</link>
		<comments>http://serveradmins.net/tuning-xcache-for-fun-and-profit/#comments</comments>
		<pubDate>Mon, 08 Jun 2009 06:36:03 +0000</pubDate>
		<dc:creator>chrism</dc:creator>
				<category><![CDATA[Miscellaneous]]></category>
		<category><![CDATA[XCache Xcache.ini php optimization tuning opcode]]></category>

		<guid isPermaLink="false">http://www.serveradmins.net/blog/?p=25</guid>
		<description><![CDATA[The hows and whys of the most basic variables to successfully tuning XCache for your installation.]]></description>
			<content:encoded><![CDATA[<p>In our first installation in this blog, we went through a basic XCache installation with CentOS, Apache and PHP 5.  Now, we&#8217;re going to look into how to make it work for your personal installation.</p>
<p>Much like every other tutorial out there, if you explicitly follow the instructions you find on the internet, you&#8217;re usually going to run into problems.  One of the biggest problems I see in systems configurations, is getting someone that &#8220;tunes&#8221; the machine by copying and pasting configs straight from a forum or blog.   Sure, it works, but that doesn&#8217;t mean it works *good*.  It could also cause many more problems that it solves.</p>
<p>The best way to tune a machine will always be understanding what you&#8217;re doing.  And that&#8217;s what we&#8217;re going to try to do here today with XCache.  So, let&#8217;s take a look at that xcache.ini file we setup in the last post.</p>
<p><code><br />
[xcache-common]</p>
<p>zend_extension = /usr/lib/php/modules/xcache.so</p>
<p>[xcache.admin]<br />
xcache.admin.enable_auth = On<br />
xcache.admin.user = "admin"<br />
; xcache.admin.pass = md5(a5851d1f3a3cff5a42b3163a7c45e5ae)<br />
xcache.admin.pass = "blahblahblahblahblah"</p>
<p>[xcache]<br />
; ini only settings, all the values here is default unless explained</p>
<p>; select low level shm/allocator scheme implemenation<br />
xcache.shm_scheme =        "mmap"<br />
; to disable: xcache.size=0<br />
; to enable : xcache.size=64M etc (any size > 0) and your system mmap allows<br />
xcache.size  =                32M<br />
; set to cpu count (cat /proc/cpuinfo |grep -c processor)<br />
xcache.count =                 2<br />
; just a hash hints, you can always store count(items) > slots<br />
xcache.slots =                8K<br />
; ttl of the cache item, 0=forever<br />
xcache.ttl   =                 0<br />
; interval of gc scanning expired items, 0=no scan, other values is in seconds<br />
xcache.gc_interval =           0</p>
<p>; same as aboves but for variable cache<br />
xcache.var_size  =            0M<br />
xcache.var_count =             1<br />
xcache.var_slots =            8K<br />
; default ttl<br />
xcache.var_ttl   =             0<br />
xcache.var_maxttl   =          0<br />
xcache.var_gc_interval =     300</p>
<p>xcache.test =                Off<br />
; N/A for /dev/zero<br />
xcache.readonly_protection = Off<br />
; for *nix, xcache.mmap_path is a file path, not directory.<br />
; Use something like "/tmp/xcache" if you want to turn on ReadonlyProtection<br />
; 2 group of php won't share the same /tmp/xcache<br />
; for win32, xcache.mmap_path=anonymous map name, not file path<br />
xcache.mmap_path =    "/tmp/xcache"</p>
<p>; leave it blank(disabled) or "/tmp/phpcore/"<br />
; make sure it's writable by php (without checking open_basedir)<br />
xcache.coredump_directory =   ""</p>
<p>; per request settings<br />
xcache.cacher =               On<br />
xcache.stat   =               On<br />
xcache.optimizer =           Off</p>
<p>[xcache.coverager]<br />
; per request settings<br />
; enable coverage data collecting for xcache.coveragedump_directory and xcache_coverager_start/stop/get/clean() functions (will hurt executing performance)<br />
xcache.coverager =          Off</p>
<p>; ini only settings<br />
; make sure it's readable (care open_basedir) by coverage viewer script<br />
; requires xcache.coverager=On<br />
xcache.coveragedump_directory = ""<br />
</code></p>
<p>The first thing we&#8217;ll look at is the xcache.count variable in the xcache.ini file.  To put it simply, think of every one of these caches as a bucket.  In these buckets you have marbles.  Now, I&#8217;m going to hand you 200 marbles, all of different colors and dump them into your buckets, dispersed evenly.  After that, you have to find the blue marble in your bucket(s).   Now, if you have 8 buckets, each with a helper to look through it, you&#8217;re going to find that blue marble FAST.   One bucket and one person searching, yeah, grab a snickers, it&#8217;ll be awhile. <img src='http://serveradmins.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>In this analogy, the buckets are the caches, and the marbles are your PHP scripts (after they&#8217;ve been compiled and stored in memory).  When your webserver gets a request for blah.php, it hands off to your PHP Handler (whatever that may be), which first references the xcache extension before trying to actually compile and serve the script.  Your limit on buckets is the number of processors you can have that can execute an instruction at the same time.  So, as the xcache.ini says, <code>cat /proc/cpuinfo | grep -c processor</code> will give you how many xcache queues you can have at once.   Personally, I always subtract at least one proc in multicore/hyperthreaded setups, simply because there&#8217;s always more going on with your machine than processsing PHP/XCache requests.  The reality is that you&#8217;ll *never* have all of your procs handling that request at the same time.  Save some CPU cycles for other stuff. <img src='http://serveradmins.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>Next up is the xcache.slots variable.   This is basically a big hash table, or index of the items stored in your &#8220;buckets&#8221; from above.  To visualize it, think about it as if you had a string tied to each marble in the above scenario, with a tag that says &#8220;blue, green, red&#8221;.  The bigger the hash table, the more strings you have to tie to marbles.   You&#8217;ll notice quicker seek times for the precompiled opcode by increasing this variable.   Each &#8220;bucket&#8221; can hold a lot of marbles (opcode) and this is just a way of finding those pieces of opcode even faster.  The hash tables don&#8217;t take up too much memory, so if you throw 32-64k at it, you&#8217;ll probably be good.   Play around and see. <img src='http://serveradmins.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>So, that&#8217;s how the how and why of your xcache.count and xcache.slots variables.  Don&#8217;t set it too high, Don&#8217;t set it too low, set it just right.</p>
<p>Now, your next most important piece is going to be the Size.   This is the total amount of ram you provide in the <code>xcache.size</code> variable.   The sole purpose of this variable is to allocate a specific amount of memory strictly for storing pre-compiled PHP scripts.  For the most part, these don&#8217;t take up much space in memory at all (as you&#8217;ll see), so throwing a bit of ram at this is a VERY important item.</p>
<p>If your site is live, and you&#8217;re serving out PHP, then you&#8217;ve already started collecting the necessary statistics to judge if you&#8217;ve allocated enough memory here.  The two biggest tells are the &#8220;Avail&#8221; and &#8220;OOMs&#8221; columns.   If you have 0.00M available in all of your queues, then you&#8217;re probably seeing increasing numbers in the OOMs column.    What this means is that XCache has stored so many compiled PHP scripts in the chunk of memory that you gave it, that it just ran out of room.   When this happens, any PHP requested by the webserver that&#8217;s not already in the cache is going to be interpreted normally.  No Caching.  This is bad. <img src='http://serveradmins.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>In order to tune this variable correctly, throw a bit more memory than the initial 16M we threw at it in our initial config.   Go ahead and double it, I&#8217;m sure you can justify the 32M of RAM here. <img src='http://serveradmins.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' />     Restart apache for the changes to take effect, and watch again.    Does it fill up?  Any OOMs?    If not, just let it go and run for a few hours.  You&#8217;re looking for the sweet spot to where you always have a bit of Available memory, and not hitting any OOMs, that&#8217;s when XCache is working at peak efficiency.</p>
<p>So, let&#8217;s say you have a HUGE site.  Thousands upon Thousands of PHP scripts, all that need compiled and cached.   You have the option of playing the ante up game, or looking down the config just a bit. <img src='http://serveradmins.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' />   The two next most important options as I see it are the <code>xcache.ttl</code> and the <code>xcache.gc_interval</code> config options.</p>
<p>These main goal of these two variables is to 1.  Set an &#8220;expiration date&#8221; on your compiled code and 2. Clean it out of the memory after it expires.  Both of these options are in seconds and disabled by default.    In a perfect world, you could fit your entire website, post-compilation into 32-64M of ram and would never have to flush it.   However, this isn&#8217;t a perfect world.  If you&#8217;ve thrown all the memory that you can safely dedicate to this that you can, then this is the next options you should tune.     The tuning here truly depends on how busy your site is.  If you have 1000 PHP scripts, room to store 800 in memory and a busy site with fairly dispersed hits, then you might need to up the TTL to something like 60 seconds and th GC frequency up to every 4 minutes or so.</p>
<p>When an opcode cache is marked as expired, it sits in your queue until the next run of the GC (garbage collector, fwiw).   The next time it is called, you&#8217;ll need to recompile it again and re-insert it into memory.   So as you can see, you don&#8217;t want to set the TTL to low here otherwise you&#8217;ll see your box more loaded than it should be because it&#8217;s re-compiling PHP it shouldn&#8217;t be.</p>
<p>Now, the next issue isn&#8217;t so much of a performance concern (to a small degree I guess, but it&#8217;s negligible, really&#8230;) is the <code>xcache.readonly_protection</code> flag.   By default this is set to Off.    What&#8217;s going on here, is involving the mmap caching for the compiled php opcode.   If set to Off, Xcache can modify files in memory rather than ditching the full opcode and recompiling if it needs to make a change.   </p>
<p>The tradeoff here is security.   With this set to On, you&#8217;re going to end up recompiling opcode for a slight adjustment, as opposed to making the adjustment.   This also means that should there be some sort of hack or compromise that allows an attacker to modify any data in your caches (think someone editing your PHP on the server directly without your permission) that they simply can&#8217;t.    </p>
<p>These updates don&#8217;t happen to often, hence the negligible performance hit.   So please, enable this unless you really need to disable it. <img src='http://serveradmins.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>With this in mind, you have the core essentials to XCache down.  There are, of course, variables I didn&#8217;t discuss here, and as you see, I didn&#8217;t just give you a generic config to copy and paste.   I&#8217;ve given you the information necessary to tune the heck out of your XCache installation.</p>
<p>Go forth and serve&#8230; (precompiled opcode. =P)</p>
]]></content:encoded>
			<wfw:commentRss>http://serveradmins.net/tuning-xcache-for-fun-and-profit/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
	</channel>
</rss>
<!-- WP Super Cache is installed but broken. The path to wp-cache-phase1.php in wp-content/advanced-cache.php must be fixed! -->