<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom">
    <title>Mr. Muskrat</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/" />
    <link rel="self" type="application/atom+xml" href="http://blogs.perl.org/users/mr_muskrat/atom.xml" />
    <id>tag:blogs.perl.org,2009-11-03:/users/mr_muskrat//179</id>
    <updated>2013-02-10T02:34:56Z</updated>
    <subtitle>A blog about the Perl programming language</subtitle>
    <generator uri="http://www.sixapart.com/movabletype/">Movable Type Pro 4.38</generator>

<entry>
    <title>GitHub for _____</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2013/02/github-for.html" />
    <id>tag:blogs.perl.org,2013:/users/mr_muskrat//179.4301</id>

    <published>2013-02-10T02:26:50Z</published>
    <updated>2013-02-10T02:34:56Z</updated>

    <summary>Earlier today I wanted to install git on Windows so that I could keep my distroprefs synced between smokers. I almost installed Git for Windows but I waited. A little bit ago, I was asked to test a new version...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>Earlier today I wanted to install git on Windows so that I could keep my distroprefs synced between smokers. I almost installed <a href="http://msysgit.github.com/">Git for Windows</a> but I waited. </p>

<p>A little bit ago, I was asked to test a new version of Net::Printer (after I submitted a bug four days ago that the tests were hanging on Windows) which resided in a GitHub repo. There was this shiny button labeled "Clone in Windows" which I clicked. I was taken to <a href="http://windows.github.com/">GitHub for Windows</a> which I downloaded and installed. I already like this better than the last time I used Git for Windows (not that it is bad). Now that I've got it installed, I seem to remember seeing this before so I guess I had just forgotten about it.</p>

<p>It turns out that there is also <a href="http://mac.github.com/">GitHub for Mac</a>, <a href="http://eclipse.github.com/">Git in Eclipse</a> and <a href="http://mobile.github.com/">GitHub Mobile</a>. Pretty cool.</p>]]>
        
    </content>
</entry>

<entry>
    <title>Smoke Testing &amp; CPAN prefs (a lesson learned)</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2013/02/smoke-testing-cpan-prefs-a-lesson-learned.html" />
    <id>tag:blogs.perl.org,2013:/users/mr_muskrat//179.4300</id>

    <published>2013-02-09T21:59:54Z</published>
    <updated>2013-02-09T22:11:41Z</updated>

    <summary>I started smoke testing on Windows a short time ago. I already had Strawberry Perl 5.12.3 and CPAN::Reporter. I installed CPAN::Reporter::Smoker and started it up. Then I did the same thing on my laptop that was running Strawberry Perl 5.16.2....</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>I started smoke testing on Windows a short time ago. I already had Strawberry Perl 5.12.3 and CPAN::Reporter. I installed CPAN::Reporter::Smoker and started it up. </p>

<p>Then I did the same thing on my laptop that was running Strawberry Perl 5.16.2.</p>

<p>I quickly discovered that many modules will hang during the make or make test phase. I looked around the CPAN Testers Wiki and found out about Distroprefs (http://wiki.cpantesters.org/wiki/Distroprefs). I didn't pull down anyone's repo though. I just started compiling a list of my own one by one as I encountered problems (making sure to check for bug reports too). </p>

<p>After a few days, I had pretty much the same list of hanging modules on both PCs. I thought "hey, I already have Dropbox installed on both computers, why not just link the prefs to a directory under Dropbox?" </p>

<p>Open a command prompt with Administrator rights and run:<br />
    mklink /D target source</p>

<p>For me that was:<br />
    mklink /D c:\strawberry\cpan\prefs c:\Users\mmusgrove\Dropbox\prefs</p>

<p>I'd maintain one copy of the distroprefs files and it would be used by two smokers. I added a few more entries to disable things like ACME and Task modules. It worked really well. </p>

<p>I decided to finally switch away from 5.12.3 so I uninstalled it and installed a 64-bit copy of Strawberry Perl 5.16.2 on one of the PCs. As I started setting up Task::CPAN::Reporter I thought that I would need to enable Task modules before it would install. </p>

<p>That's when I noticed that using Dropbox for such a task is not a good idea unless you remember to remove the link before uninstalling Strawberry Perl. D'oh.<br />
</p>]]>
        
    </content>
</entry>

<entry>
    <title>File::LinkDir 1.02</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2012/05/filelinkdir-102.html" />
    <id>tag:blogs.perl.org,2012:/users/mr_muskrat//179.3257</id>

    <published>2012-05-17T16:55:45Z</published>
    <updated>2012-05-17T16:59:58Z</updated>

    <summary>File::LinkDir 1.02 is on its way to a CPAN mirror near you. Two changes went into this release. - The link-file script will be installed now. (Hinrik) - The --add-ignore option works properly now. (Matt) I&apos;d like to thank Philip...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>File::LinkDir 1.02 is on its way to a CPAN mirror near you.</p>

<p>Two changes went into this release.<br />
- The link-file script will be installed now. (Hinrik)<br />
- The --add-ignore option works properly now. (Matt)</p>

<p>I'd like to thank Philip Durbin for pointing out that --add-ignore wasn't working properly.</p>]]>
        
    </content>
</entry>

<entry>
    <title>perlbrew and tmux</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2012/05/perlbrew-and-tmux.html" />
    <id>tag:blogs.perl.org,2012:/users/mr_muskrat//179.3194</id>

    <published>2012-05-03T07:51:58Z</published>
    <updated>2012-05-03T08:01:41Z</updated>

    <summary>Tonight I decided to install a variety of perl versions on the desktop PC where I run Arch Linux. Rather than kick them all off manually, I whipped up a bash script wrapper around perlbrew. It loops through all of...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>Tonight I decided to install a variety of perl versions on the desktop PC where I run Arch Linux. Rather than kick them all off manually, I whipped up a bash script wrapper around perlbrew. </p>

<p>It loops through all of the versions of perl I'm interested in. It starts perlbrew with the specified options but backgrounded. When the build.log shows up, it sends keystrokes to tmux window 4 telling it tail the build.log and brings perlbrew to the foreground. When the install is finished, it sends keystrokes to tmux window 4 telling it stop tailing the file and moves the build.log out of the way so we can view it later.</p>

<p><a href="http://blogs.perl.org/users/mr_muskrat/perlinstall.sh.txt">perlinstall.sh</a></p>]]>
        
    </content>
</entry>

<entry>
    <title>Oracle SESSIONS_PER_USER</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2012/04/oracle-sessions-per-user.html" />
    <id>tag:blogs.perl.org,2012:/users/mr_muskrat//179.3176</id>

    <published>2012-04-30T18:26:06Z</published>
    <updated>2012-04-30T18:38:37Z</updated>

    <summary>Connecting to Oracle with a proxy connection like this: DBI-&gt;connect( $dsn, &apos;user[otheruser]&apos;, &apos;password&apos;, $option_list) We recently updated DBI to 1.620 and DBD::Oracle to 1.44 (late last week I think). Today I saw an error that I have never seen before...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>Connecting to Oracle with a proxy connection like this:<br />
    DBI->connect( $dsn, 'user[otheruser]', 'password', $option_list)</p>

<p>We recently updated DBI to 1.620 and DBD::Oracle to 1.44 (late last week I think). Today I saw an error that I have never seen before (but should have). "ORA-02391: exceeded simultaneous SESSIONS_PER_USER limit"  You see otheruser has a profile that limits SESSIONS_PER_USER to one. We're creating between one and eleven of these database connections simultaneously in different processes.</p>

<p>So I tried it with the older install that was using DBI 1.616 and DBD::Oracle 1.30. I didn't receive the error so it appears that the SESSIONS_PER_USER profile limit was not being respected. </p>

<p>We're bumping up the SESSIONS_PER_USER where appropriate and adding some checks for this error condition now that it's being thrown.</p>

<p>I'm curious if anyone is aware of which change may have caused this to start working correctly?</p>]]>
        
    </content>
</entry>

<entry>
    <title>Yet Another Society Website</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2012/04/yet-another-society-website.html" />
    <id>tag:blogs.perl.org,2012:/users/mr_muskrat//179.3060</id>

    <published>2012-04-07T15:49:03Z</published>
    <updated>2012-04-07T16:00:50Z</updated>

    <summary>So I did a search for Yet Another Society today and the first hit is http://www.yetanother.org. (No real surprise there.) I click the link and (surprise!) am greeted by a page that was last updated in 2003 and every link...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>So I did a search for Yet Another Society today and the first hit is <a href="http://www.yetanother.org">http://www.yetanother.org</a>. (No real surprise there.) I click the link and (surprise!) am greeted by a page that was last updated in 2003 and every link that doesn't point to static content is broken.</p>

<p>Who maintains <a href="http://www.yetanother.org">http://www.yetanother.org</a> these days? I emailed kevinm@yetanother.org (the only email address found) but it bounced.</p>

<p>At a minimum, it should redirect to <a href="http://www.perlfoundation.org">http://www.perlfoundation.org</a>. Ideally some of the original content would remain that explains the relationship between Yet Another Society and The Perl Foundation as well as relevant links to other parts of the Perl community.</p>]]>
        
    </content>
</entry>

<entry>
    <title>Vim Screenshot</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2012/03/vim-screenshot.html" />
    <id>tag:blogs.perl.org,2012:/users/mr_muskrat//179.2959</id>

    <published>2012-03-19T22:26:14Z</published>
    <updated>2012-03-19T22:42:21Z</updated>

    <summary>As requested in the Fight Night post, here is a screenshot of a Perl file loaded in Vim (in this case CGI::Simple)....</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    <category term="vimyapcnafightnight" label="vim yapc::na &quot;fight night&quot;" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>As requested in the <a href="http://blog.yapcna.org/post/19587778761/fight-night">Fight Night</a> post, here is a screenshot of a Perl file loaded in Vim (in this case CGI::Simple).</p>

<p><a href="http://blogs.perl.org/users/mr_muskrat/assets_c/2012/03/vim-751.html" onclick="window.open('http://blogs.perl.org/users/mr_muskrat/assets_c/2012/03/vim-751.html','popup','width=1280,height=962,scrollbars=no,resizable=no,toolbar=no,directories=no,location=no,menubar=no,status=no,left=0,top=0'); return false"><img src="http://blogs.perl.org/users/mr_muskrat/assets_c/2012/03/vim-thumb-640x481-751.png" width="640" height="481" alt="Vim" class="mt-image-none" style="" /></a></p>]]>
        
    </content>
</entry>

<entry>
    <title>Switching to Notepad++</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2012/02/switching-to-notepad.html" />
    <id>tag:blogs.perl.org,2012:/users/mr_muskrat//179.2773</id>

    <published>2012-02-05T17:23:45Z</published>
    <updated>2012-02-05T17:31:58Z</updated>

    <summary>When programming on a Windows PC, I use Metapad (http://liquidninja.com/metapad/) as I have for about a decade. (I used EditPad Lite prior to finding Metapad.) Recently at home I have been using Notepad++ and it&apos;s really grown on me. I&apos;ve...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>When programming on a Windows PC, I use Metapad (http://liquidninja.com/metapad/) as I have for about a decade. (I used EditPad Lite prior to finding Metapad.) </p>

<p>Recently at home I have been using Notepad++ and it's really grown on me. I've always liked having all of my open documents in tabs. It also has syntax highlighting which really helps me see mistakes before I've even tried a compilation check.</p>

<p>I'm going to install it on my work laptop and see how it works out for me.</p>]]>
        
    </content>
</entry>

<entry>
    <title>Debugging ORA-12157</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2011/11/debugging-ora-12157.html" />
    <id>tag:blogs.perl.org,2011:/users/mr_muskrat//179.2410</id>

    <published>2011-11-07T22:48:23Z</published>
    <updated>2011-11-07T23:18:48Z</updated>

    <summary>Does anyone reading this have experience with debugging ORA-12157 TNS Internal network communication error? Googling for it isn&apos;t really helpful. I get a bunch of pages that say the same thing as the Oracle docs (turn on tracing and reproduce...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>Does anyone reading this have experience with debugging ORA-12157 TNS Internal network communication error? </p>

<p>Googling for it isn't really helpful. I get a bunch of pages that say the same thing as the Oracle docs (turn on tracing and reproduce the issue). </p>

<p>The problem is that we don't see it consistently enough to even know to reproduce it properly much less create a minimal test case.</p>

<p>Update:<br />
I looked in the alert.log and found a few "ORA-609 : opiodr aborting process unknown ospid" errors each with a corresponding trace file that ends with "opiino: Attach failed due to ORA-12537".<br />
</p>]]>
        
    </content>
</entry>

<entry>
    <title>So your web app double posts?</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2011/04/so-your-web-app-double-posts.html" />
    <id>tag:blogs.perl.org,2011:/users/mr_muskrat//179.1684</id>

    <published>2011-04-21T21:33:15Z</published>
    <updated>2011-04-21T21:57:52Z</updated>

    <summary>This post is just in case I forget this again in the future. Hopefully, I&apos;ll find it when I search the net for this issue. This post is testament of my tenacity (more like my stupidity when I let myself...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    <category term="cgi" label="cgi" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="doublepost" label="double post" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="mod_perl" label="mod_perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="mojolicious" label="mojolicious" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="webapp" label="web app" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>This post is just in case I forget this again in the future. Hopefully, I'll find it when I search the net for this issue. </p>

<p>This post is testament of my tenacity (more like my stupidity when I let myself get mentally exhausted).</p>

<p>I have been working on integrating some Mojolicious apps into our existing Apache CGI/mod_perl set of applications. When I went to test the latest version of a particular app, that changed how things were added, I decided to put some warn statements in to see if I had the flow right. Looking in the error log, I started seeing everything happening twice! </p>

<p>The methods that get used to create the initial view. The methods that get used to add a new item and subsequently view it. Everything.</p>

<p>I walked through my app and couldn't find any obvious reason for the odd behavior. I double-checked my templates but found nothing. I spent the better part of two hours searching the net, looking at the Mojolicious docs, Apache docs and tweaking my Apache config. All because I was sure that was where the problem resided; after all, Mojolicious wasn't originally intended to be used that way.</p>

<p>At the two hour mark, I asked a few people if they had any ideas. We walked through the same things again together and yet found nothing that should cause this weirdness. </p>

<p>I then put some warns in some of our mod_perl apps only to find the same thing was happening there as well. </p>

<p>I added a new CGI script that did nothing but print a content-type, warn "hello\n" and print "hi\n". When I accessed it, sure enough, I saw "hello" in the error log twice.</p>

<p>I switched the server I was working on, thinking that surely something was just really wrong with my Apache install on the server. Nope, I saw the same exact behavior.</p>

<p>I had my co-worker access my sandbox and the warns were only showing up once. Lightbulb time!</p>

<p>I refined my search and found that someone had the same sort of problem with Firebug a while back. I looked at the status bar and found that Firebug was disabled... but YSlow was enabled. </p>

<p>I disabled YSlow and restarted Firefox. I accessed the pages and sure enough, the warns all showed up once. For extra validation, my co-worker enabled YSlow and hit the pages. The warns did indeed happen twice for her.</p>

<p>So if you use YSlow, turn it off when you are not actively testing page loads or you too might spend a stupid amount of time tracking down what amounts to the intended behavior of a browser add-on.  (YSlow loads the page once using the cache and once without so that it can compare the two.)<br />
</p>]]>
        
    </content>
</entry>

<entry>
    <title>Perl is dead? Great! Now get back to work.</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2011/03/perl-is-dead-great-now-get-back-to-work.html" />
    <id>tag:blogs.perl.org,2011:/users/mr_muskrat//179.1562</id>

    <published>2011-03-16T15:45:50Z</published>
    <updated>2011-03-16T15:52:27Z</updated>

    <summary>Seth Godin has an interesting take on &quot;____ is dead&quot; in his blog post, &quot;Bring me stuff that&apos;s dead, please&quot;. To paraphrase him, no real work is done until an innovation is dead. So the next time you hear that...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>Seth Godin has an interesting take on "____ is dead" in his blog post, <a href="http://sethgodin.typepad.com/seths_blog/2011/03/bring-me-stuff-thats-dead-please.html">"Bring me stuff that's dead, please"</a>. To paraphrase him, no real work is done until an innovation is dead. So the next time you hear that Perl is dead, just laugh it off and get back to work. I know that I will.</p>]]>
        
    </content>
</entry>

<entry>
    <title>mod_perl2 &amp; Devel::NYTProf</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2011/01/mod-perl2-develnytprof.html" />
    <id>tag:blogs.perl.org,2011:/users/mr_muskrat//179.1401</id>

    <published>2011-01-26T22:02:43Z</published>
    <updated>2011-01-26T22:33:22Z</updated>

    <summary>This week I&#8217;ve been trying to switch us over to using mod_perl2. I wanted to cache database handles as much as possible so one of the first things that I did was edit my startup.pl and add: use Apache::DBI; Most...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>This week I&#8217;ve been trying to switch us over to using mod_perl2. I wanted to cache database handles as much as possible so one of the first things that I did was edit my startup.pl and add:</p>

<pre><code>use Apache::DBI;
</code></pre>

<p>Most stuff just works. When I find something that is only slightly broken, I fix it. When I find something that is horribly broken, I just create a Location in httpd.conf to tell Apache to run that as plain CGI and I&#8217;ll update them later.</p>

<p>The entire application suite feels faster. I suspect much of the speed up is due to caching database handles but I&#8217;d like to profile it. I have no problems profiling CGI with Devel::NYTProf. When I configure httpd.conf to use Devel::NYTProf::Apache like this I get issues. </p>

<pre><code>PerlSetEnv NYTPROF trace=2:file=/tmp/mm-nytprof.out:addpid=1:start=begin:use_db_sub=1
PerlModule Devel::NYTProf::Apache
</code></pre>

<p>I guess I&#8217;ll have to file a bug report. Here is just one of the many issues showing up in the error log:</p>

<pre><code>Marking 'Apache2::RequestRec::args' as xsub
Marking 'CGI::Cookie::CORE:subst' as sop
Marking 'CGI::Cookie::CORE:substcont' as sop
NYTProf is confused about CV 0x2ac1ed3023e0 called as /opt/perl/lib/site_perl/5.12.3/x86_64-linux-thread-multi/ModPerl/RegistryCooker.pm at /opt/perl/lib/site_perl/5.12.3/x86_64-linux-thread-multi/ModPerl/RegistryCooker.pm line 225 (please report as a bug)
SV = PVCV(0x2ac1ed2b49d0) at 0x2ac1ed3023e0
  REFCNT = 2
  FLAGS = (POK,pPOK,CONST)
  PROTOTYPE = ""
  COMP_STASH = 0x2ac1ed240ad0   "ModPerl::RegistryCooker"
  XSUB = 0x2ac1d2d845b0
  XSUBANY = 0x2ac1ed2d0da8 (CONST SV)
    SV = IV(0x2ac1ed2d0da0) at 0x2ac1ed2d0da8
      REFCNT = 2
      FLAGS = (PADMY,IOK,READONLY,pIOK)
      IV = 0
  GVGV::GV = 0x2ac1ed2d2910     ""
  FILE = "/opt/perl/lib/site_perl/5.12.3/x86_64-linux-thread-multi/ModPerl/RegistryCooker.pm"
  DEPTH = 0
  FLAGS = 0xc00
  OUTSIDE_SEQ = 0
  PADLIST = 0x0
  OUTSIDE = 0x0 (null)
unknown entersub xsub assumed to be anon called_cv '/opt/perl/lib/site_perl/5.12.3/x86_64-linux-thread-multi/ModPerl/RegistryCooker.pm'
</code></pre>

<p>Is there a way to tell Devel::NYTProf not to profile ModPerl::RegistryCooker?</p>
]]>
        

    </content>
</entry>

<entry>
    <title>TAP</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2011/01/tap.html" />
    <id>tag:blogs.perl.org,2011:/users/mr_muskrat//179.1304</id>

    <published>2011-01-04T20:49:49Z</published>
    <updated>2011-01-04T21:05:33Z</updated>

    <summary>A recent push at work has been to use TAP everywhere that we need to test something. It&apos;s great for a variety of reasons. We are finally trying to test as much as possible. All of the myriad pieces of...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    <category term="tap" label="TAP" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>A recent push at work has been to use <a href="http://testanything.org/wiki/index.php/Main_Page">TAP</a> everywhere that we need to test something. It's great for a variety of reasons.</p>

<ul>
	<li>We are finally trying to test as much as possible.</li>
	<li>All of the myriad pieces of software, written in a variety of languages, can use the same text-based interface.</li>
	<li>Anyone in the group can look at the output and understand it.</li>
	<li>The test results can be read by a single process that parses and displays the results in a uniform fashion.</li>
</ul>

<p>It's very refreshing to hear C++ programmers talking about TAP.<br />
</p>]]>
        
    </content>
</entry>

<entry>
    <title>Chained Gradients</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2010/12/chained-gradients.html" />
    <id>tag:blogs.perl.org,2010:/users/mr_muskrat//179.1234</id>

    <published>2010-12-09T03:46:38Z</published>
    <updated>2010-12-09T04:12:26Z</updated>

    <summary>Earlier I replied to Ovid&#8217;s post Perl101: Red to Green Gradient about how to create a gradient that is closer to being accurate. (Rafaël had pointed out that Ovid&#8217;s didn&#8217;t properly deal with hue and intensity.) The problem with the...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>Earlier I <a href="http://blogs.perl.org/users/ovid/2010/12/perl101-red-to-green-gradient.html#comment-5836">replied</a> to Ovid&#8217;s post <a href="http://blogs.perl.org/users/ovid/2010/12/perl101-red-to-green-gradient.html">Perl101: Red to Green Gradient</a> about how to create a gradient that is closer to being accurate. (Rafaël had pointed out that Ovid&#8217;s didn&#8217;t properly deal with hue and intensity.) The problem with the more accurate approach is that Ovid wanted one that shifted from red to yellow to green and my version did not do that. </p>

<p>So I give you a better (although still not 100% accurate) solution. It has not yet been optimized. It may have bugs. Your mileage may vary. Some conditions and limitations may apply. Yadda yadda yadda.</p>

<pre><code>#!/usr/bin/env perl
use strict;
use warnings;
use List::Util qw( min max );

my $red     = [ 0xFF, 0x00, 0x00 ];
my $yellow  = [ 0xFF, 0xFF, 0x00 ];
my $green   = [ 0x00, 0xFF, 0x00 ];
my $cyan    = [ 0x00, 0xFF, 0xFF ];
my $blue    = [ 0x00, 0x00, 0xFF ];
my $magenta = [ 0xFF, 0x00, 0xFF ];

my $steps = 16;

#my $colors = chained_gradients( $steps * 3, $red, $green, $blue ); # change me!
my $colors = chained_gradients( $steps * 2, $red, $yellow, $green ); # change me!
#my $colors = chained_gradients( $steps, $red, $green ); # change me!

open my $html, '&gt;', 'colors.html';
print $html "&lt;html&gt;&lt;head&gt;&lt;title&gt;colors&lt;/title&gt;&lt;/head&gt;&lt;body&gt;&lt;table&gt;\n";
for my $color ( @{ $colors } )
{
    printf "%02X%02X%02X  [ %1\$3s, %2\$3s, %3\$3s ]  h: %3s, s: %3s, v: %3s\n", @{ $color }, @{ to_hsv( $color ) };
    printf $html qq{&lt;tr&gt;&lt;td style="background-color:#%02X%02X%02X"&gt;%1\$02X%2\$02X%3\$02X&lt;/td&gt;&lt;/tr&gt;\n}, @{ $color };
}
print $html "&lt;/table&gt;&lt;/body&gt;&lt;/html&gt;\n";
close $html;

sub step
{
    my ( $steps, $first, $last ) = @_;

    $steps--;

    my $sign = $last &lt;=&gt; $first;
    my $step = $first == $last ? 0 : int( ( $first + $last ) / $steps );

    return $sign == 0 ? $step : $sign * $step;
}

sub gradient
{
    my ( $steps, $first, $last ) = @_;

    my $step = [ 
    step( $steps, $first-&gt;[0], $last-&gt;[0] ), 
    step( $steps, $first-&gt;[1], $last-&gt;[1] ), 
    step( $steps, $first-&gt;[2], $last-&gt;[2] ),
    ];

    my $gradients = [ ( undef ) x $steps ];
    for my $curr ( 0 .. $#{ $gradients } )
    {
    my $prev = $curr - 1;
    if ( $curr == 0 )
    {
        $gradients-&gt;[$curr] = $first;
    }
    elsif ( $curr == $#{ $gradients } )
    {
        $gradients-&gt;[$curr] = $last;
    }
    else
    {
        $gradients-&gt;[$curr] = [ 
            $gradients-&gt;[$prev][0] + $step-&gt;[0], 
            $gradients-&gt;[$prev][1] + $step-&gt;[1], 
            $gradients-&gt;[$prev][2] + $step-&gt;[2],
        ];
    }
    }

    return $gradients;
}

sub chained_gradients
{
    my ( $steps, @colors ) = @_;

    my $max = $#colors;
    $steps = int( $steps / $max );
    my $sections = $#colors - 1;

    my @gradients;
    while ( @colors &gt;= 2 )
    {
    my $start = shift @colors;
    my $end = $colors[0];
    my $step = ( @colors == $max ) ? $steps + 1 : $steps;

    push @gradients, gradient( $step, $start, $end );
    }

    for my $curr ( 1 .. $sections )
    {
    my $prev = $curr - 1;
    my $ndx = ( $curr == 1 ) ? $steps : $steps - 1;
    if (
        $gradients[$curr]-&gt;[0][0] == $gradients[$prev]-&gt;[$ndx][0] &amp;&amp;
        $gradients[$curr]-&gt;[0][1] == $gradients[$prev]-&gt;[$ndx][1] &amp;&amp;
        $gradients[$curr]-&gt;[0][2] == $gradients[$prev]-&gt;[$ndx][2]
    )
    {
        $#{ $gradients[$prev] }--;
    }
    }

    my $gradients;
    for my $i ( 0 .. $max )
    {
    my $grad = $gradients[$i];
    for my $j ( 0 .. $#{ $grad } )
    {
        push @{ $gradients }, $grad-&gt;[$j];
    }
    }

    return $gradients;

}

# Algorithm found at http://www.cs.rit.edu/~ncs/color/t_convert.html
sub to_hsv 
{
    my $color = shift;
    my ( $h, $s, $v );

    my $min = min( @{ $color } );
    my $max = max( @{ $color } );

    $v = int( ( $max / 255 ) * 100 );

    my $delta = $max - $min;

    if ( $max == 0 )
    {
    # red = green = blue = 0 
    # s = 0, v is undef
    $s = 0;
    $h = -1;
    }
    else
    {
    $s = int( ( $delta / $max ) * 100 );

    if ( $color-&gt;[0] == $max )
    {
        $h = ( $color-&gt;[1] - $color-&gt;[2] ) / $delta; # between yellow &amp; magenta
    }
    elsif ( $color-&gt;[1] == $max )
    {
        $h = 2 + ( $color-&gt;[2] - $color-&gt;[0] ) / $delta; # between cyan &amp; yellow
    }
    else
    {
        $h = 4 + ( $color-&gt;[0] - $color-&gt;[1] ) / $delta; # between magenta &amp; cyan
    }

    $h = int ( $h * 60 ); # degrees

    if ( $h &lt; 0 )
    {
        $h += 360;
    }

    }

    return [ $h, $s, $v ];
}
</code></pre>

<p>It will print out the hex, RGB and HSV values for the colors you pass into chained_gradients. It also creates a very basic HTML file containing a table of your colors.</p>

<p>Here&#8217;s the output.</p>

<pre><code>FF0000  [ 255,   0,   0 ]  h:   0, s: 100, v: 100
FF0F00  [ 255,  15,   0 ]  h:   3, s: 100, v: 100
FF1E00  [ 255,  30,   0 ]  h:   7, s: 100, v: 100
FF2D00  [ 255,  45,   0 ]  h:  10, s: 100, v: 100
FF3C00  [ 255,  60,   0 ]  h:  14, s: 100, v: 100
FF4B00  [ 255,  75,   0 ]  h:  17, s: 100, v: 100
FF5A00  [ 255,  90,   0 ]  h:  21, s: 100, v: 100
FF6900  [ 255, 105,   0 ]  h:  24, s: 100, v: 100
FF7800  [ 255, 120,   0 ]  h:  28, s: 100, v: 100
FF8700  [ 255, 135,   0 ]  h:  31, s: 100, v: 100
FF9600  [ 255, 150,   0 ]  h:  35, s: 100, v: 100
FFA500  [ 255, 165,   0 ]  h:  38, s: 100, v: 100
FFB400  [ 255, 180,   0 ]  h:  42, s: 100, v: 100
FFC300  [ 255, 195,   0 ]  h:  45, s: 100, v: 100
FFD200  [ 255, 210,   0 ]  h:  49, s: 100, v: 100
FFE100  [ 255, 225,   0 ]  h:  52, s: 100, v: 100
FFFF00  [ 255, 255,   0 ]  h:  60, s: 100, v: 100
EEFF00  [ 238, 255,   0 ]  h:  64, s: 100, v: 100
DDFF00  [ 221, 255,   0 ]  h:  68, s: 100, v: 100
CCFF00  [ 204, 255,   0 ]  h:  72, s: 100, v: 100
BBFF00  [ 187, 255,   0 ]  h:  76, s: 100, v: 100
AAFF00  [ 170, 255,   0 ]  h:  80, s: 100, v: 100
99FF00  [ 153, 255,   0 ]  h:  84, s: 100, v: 100
88FF00  [ 136, 255,   0 ]  h:  88, s: 100, v: 100
77FF00  [ 119, 255,   0 ]  h:  92, s: 100, v: 100
66FF00  [ 102, 255,   0 ]  h:  96, s: 100, v: 100
55FF00  [  85, 255,   0 ]  h: 100, s: 100, v: 100
44FF00  [  68, 255,   0 ]  h: 104, s: 100, v: 100
33FF00  [  51, 255,   0 ]  h: 108, s: 100, v: 100
22FF00  [  34, 255,   0 ]  h: 112, s: 100, v: 100
11FF00  [  17, 255,   0 ]  h: 116, s: 100, v: 100
00FF00  [   0, 255,   0 ]  h: 120, s: 100, v: 100
</code></pre>

<p>Here&#8217;s the HTML table that it generated.</p>

<table>
<tr><td style="background-color:#FF0000">FF0000</td></tr>
<tr><td style="background-color:#FF0F00">FF0F00</td></tr>
<tr><td style="background-color:#FF1E00">FF1E00</td></tr>
<tr><td style="background-color:#FF2D00">FF2D00</td></tr>
<tr><td style="background-color:#FF3C00">FF3C00</td></tr>
<tr><td style="background-color:#FF4B00">FF4B00</td></tr>
<tr><td style="background-color:#FF5A00">FF5A00</td></tr>
<tr><td style="background-color:#FF6900">FF6900</td></tr>
<tr><td style="background-color:#FF7800">FF7800</td></tr>
<tr><td style="background-color:#FF8700">FF8700</td></tr>
<tr><td style="background-color:#FF9600">FF9600</td></tr>
<tr><td style="background-color:#FFA500">FFA500</td></tr>
<tr><td style="background-color:#FFB400">FFB400</td></tr>
<tr><td style="background-color:#FFC300">FFC300</td></tr>
<tr><td style="background-color:#FFD200">FFD200</td></tr>
<tr><td style="background-color:#FFE100">FFE100</td></tr>
<tr><td style="background-color:#FFFF00">FFFF00</td></tr>
<tr><td style="background-color:#EEFF00">EEFF00</td></tr>
<tr><td style="background-color:#DDFF00">DDFF00</td></tr>
<tr><td style="background-color:#CCFF00">CCFF00</td></tr>
<tr><td style="background-color:#BBFF00">BBFF00</td></tr>
<tr><td style="background-color:#AAFF00">AAFF00</td></tr>
<tr><td style="background-color:#99FF00">99FF00</td></tr>
<tr><td style="background-color:#88FF00">88FF00</td></tr>
<tr><td style="background-color:#77FF00">77FF00</td></tr>
<tr><td style="background-color:#66FF00">66FF00</td></tr>
<tr><td style="background-color:#55FF00">55FF00</td></tr>
<tr><td style="background-color:#44FF00">44FF00</td></tr>
<tr><td style="background-color:#33FF00">33FF00</td></tr>
<tr><td style="background-color:#22FF00">22FF00</td></tr>
<tr><td style="background-color:#11FF00">11FF00</td></tr>
<tr><td style="background-color:#00FF00">00FF00</td></tr>
</table>
]]>
        

    </content>
</entry>

<entry>
    <title>Daily WTF</title>
    <link rel="alternate" type="text/html" href="http://blogs.perl.org/users/mr_muskrat/2010/12/daily-wtf.html" />
    <id>tag:blogs.perl.org,2010:/users/mr_muskrat//179.1222</id>

    <published>2010-12-02T22:44:39Z</published>
    <updated>2010-12-03T00:23:12Z</updated>

    <summary>I often read the &#8220;Daily WTF&#8221; because there&#8217;s something satisfying about seeing other people&#8217;s bad code. &#8220;See? Our code isn&#8217;t as bad as all this!&#8221; It&#8217;s not as fun when you find &#8220;Daily WTF&#8221; moments in your codebase. Today, one...</summary>
    <author>
        <name>Mr. Muskrat</name>
        
    </author>
    
    
    <content type="html" xml:lang="en" xml:base="http://blogs.perl.org/users/mr_muskrat/">
        <![CDATA[<p>I often read the &#8220;Daily WTF&#8221; because there&#8217;s something satisfying about seeing other people&#8217;s bad code. &#8220;See? Our code isn&#8217;t as bad as all this!&#8221; It&#8217;s not as fun when you find &#8220;Daily WTF&#8221; moments in your codebase.</p>

<p>Today, one of my coworkers asked about a piece of code that wasn&#8217;t giving the expected results. It&#8217;s a part of some really old code that would be done differently given the time to rewrite it. Any way, there are a series of if/elsif/else clauses that check various things. One of those things is to validate some data against a known constraint. This particular section is supposed to validate that the given data falls within the range of a valid UINT (UINT8, UINT16, etc).</p>

<pre><code>elsif ( $constraint =~ /^UINT(\d+)/ )
{   
    $start = 0;
    $end = ( 0x1 &lt;&lt; ( $1 - 1 ) );
}
</code></pre>

<p>That looks right, doesn&#8217;t it? Maybe&#8230; If you just glance at it&#8230;</p>

<p>Start with 1 and bit shift it left $1 - 1 times. So if we are validating a UINT8, we take 1 and bit shift it left 7 times which gives us&#8230; 128. Uh, that&#8217;s not right.</p>

<p>It should be written like this:</p>

<pre><code>elsif ( $constraint =~ /^UINT(\d+)/ )
{   
    $start = 0;
    $end = ( 0x1 &lt;&lt; $1 ) - 1;
}
</code></pre>

<p>Start with 1 and bit shift it left $1 times and subtract 1. So given a UINT8 again, we take a 1 and bit shift it left 8 times and subtract 1 leaving us with 255. Good.</p>

<p>It might be better if we did away with the bit shifts altogether though and did it using a power of 2 like this instead:</p>

<pre><code>elsif ( $constraint =~ /^UINT(\d+)/ )
{   
    $start = 0;
    $end = 2 ** $1 - 1;
}
</code></pre>

<p>I haven&#8217;t looked at the commit to see who made this mistake because there&#8217;s about a 50/50 chance that it was me.</p>
]]>
        

    </content>
</entry>

</feed>
