<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-35618625</id><updated>2012-02-13T11:07:53.940-03:30</updated><category term='malware'/><category term='humour'/><category term='education'/><category term='tools'/><category term='law'/><category term='bugs'/><title type='text'>Searching for Better Software</title><subtitle type='html'></subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>23</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-35618625.post-401890242812463375</id><published>2012-01-31T01:11:00.000-03:30</published><updated>2012-01-31T01:13:26.832-03:30</updated><category scheme='http://www.blogger.com/atom/ns#' term='tools'/><title type='text'>Free Software Project Hosting Comparison</title><content type='html'>There are three leading free software project hosting services. These services lead in number of hosted projects by a factor of 10 over their competition.&lt;br /&gt;&lt;br /&gt;&lt;table border="1"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td&gt;&lt;b&gt;Name&lt;/b&gt;&lt;/td&gt; &lt;td&gt;&lt;b&gt;Established&lt;/b&gt;&lt;/td&gt; &lt;td&gt;&lt;b&gt;Projects&lt;/b&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;GitHub&lt;/td&gt; &lt;td&gt;2008&lt;/td&gt; &lt;td&gt;885, 000&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;Google Code&lt;/td&gt; &lt;td&gt;2006&lt;/td&gt; &lt;td&gt;250, 000&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;SourceForge&lt;/td&gt; &lt;td&gt;1999&lt;/td&gt; &lt;td&gt;432, 000&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;a href="http://en.wikipedia.org/wiki/Comparison_of_open_source_software_hosting_facilities"&gt;&lt;span class="Apple-style-span" style="font-size: xx-small;"&gt;http://en.wikipedia.org/wiki/Comparison_of_open_source_software_hosting_facilities&lt;/span&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;For a free service like this, popularity and longevity are a good first approximation of which you should choose. A popular long lived service is likely to:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;continue to last (an important consideration)&lt;/li&gt;&lt;li&gt;have good features and usability (that is why they are popular, hopefully)&lt;/li&gt;&lt;/ol&gt;However, sometimes first approximations are wrong. When I investigated the available services I found that all three of the above leaders meet my basic requirements, most importantly they all have git interfaces. However, there was a fourth service with an important differentiator: free private repositories. Most software project hosting services support private repositories for a fee, however BitBucket by Atlassian (the JIRA guys), supports private repositories with limited contributors. This is a very attractive option because ideally I’d like to do my experimentation in private.&lt;br /&gt;&lt;br /&gt;To compare these 4 services my plan is to host an existing small project at each of them. I’ll let you know what I find out.&lt;br /&gt;&lt;br /&gt;Do you have a favourite software project hosting service that I should be considering? What is so great about it?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-401890242812463375?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/401890242812463375/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=401890242812463375' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/401890242812463375'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/401890242812463375'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2012/01/free-software-project-hosting.html' title='Free Software Project Hosting Comparison'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-4023227217660056215</id><published>2012-01-24T22:37:00.000-03:30</published><updated>2012-01-25T00:39:48.221-03:30</updated><category scheme='http://www.blogger.com/atom/ns#' term='education'/><title type='text'>Online Education</title><content type='html'>Watch this amazing video of &lt;a href="http://new.livestream.com/channels/556/videos/112950"&gt;Sebastian Thrun talking about his experiences with his recent ai-class experiment&lt;/a&gt; and &lt;a href="http://www.udacity.com"&gt;his next education project&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-4023227217660056215?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/4023227217660056215/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=4023227217660056215' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/4023227217660056215'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/4023227217660056215'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2012/01/online-education.html' title='Online Education'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-6851576164381353456</id><published>2011-07-20T11:31:00.000-02:30</published><updated>2011-07-20T11:31:51.268-02:30</updated><title type='text'>Wasted Hardware</title><content type='html'>My laptop has 8GB of RAM, or approximately 150,000 novels worth.[1] It has 2 CPUs executing a total of 10^10 instructions per second, or enough instructions to make my cursor blink for 150 years.[2] Most of the time Windows Task Manager reports CPU utilization of less than 5% and memory utilization of less than 40%.&lt;br /&gt;&lt;br /&gt;Why is my computer so lazy? Shouldn't it be doing more to help me? Wikipedia would fit in a GB of RAM or so, why do I have to look stuff up? Am I the only person depressed by the Task Manager?&lt;br /&gt;&lt;br /&gt;[1] Assume compressed ASCII English text.&lt;br /&gt;[2] Assume a sequence of on/off instructions executed 2 per second.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-6851576164381353456?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/6851576164381353456/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=6851576164381353456' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/6851576164381353456'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/6851576164381353456'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2011/07/wasted-hardware.html' title='Wasted Hardware'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-3226007788021145627</id><published>2010-05-10T13:36:00.000-02:30</published><updated>2010-05-10T13:36:07.744-02:30</updated><title type='text'>Technical Writing</title><content type='html'>Writing well is hard. It is easy to write about technical topics in an inscrutable, boring, dry way. The ability to write about technical topics in a way that is clear and holds interest is a rare gift. Here are two recent examples of good writing I've seen:&lt;br /&gt;&lt;br /&gt;Brian Hayes, &lt;a href="http://www.americanscientist.org/issues/id.3278,y.2002,no.3,content.true,page.1,css.print/issue.aspx"&gt;The Easiest Hard Problem&lt;/a&gt;. Takes a technical paper on a topic that even the experts find tough and recasts it as something that everyone can understand and find interesting.&lt;br /&gt;&lt;br /&gt;Alexey Radul, &lt;a href="http://dspace.mit.edu/bitstream/handle/1721.1/49525/MIT-CSAIL-TR-2009-053.pdf"&gt;Propagation Networks: A Flexible and&lt;br /&gt;Expressive Substrate for Computation&lt;/a&gt;. A Ph.D. dissertation on a new programming model. This one is not for the layman as the previous example, but you certainly do not need to be a Ph.D. candidate to understand or enjoy it.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-3226007788021145627?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/3226007788021145627/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=3226007788021145627' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3226007788021145627'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3226007788021145627'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/05/technical-writing.html' title='Technical Writing'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-8910597339282241394</id><published>2010-04-28T09:40:00.000-02:30</published><updated>2010-04-28T09:40:43.393-02:30</updated><title type='text'>Some US Senators Chastise Facebook</title><content type='html'>Canada has had some success getting Facebook to respect their customers' privacy, now &lt;a href="http://content.usatoday.com/communities/onpolitics/post/2010/04/senators-to-facebook-quit-sharing-users-info/1"&gt;some US senators are requesting change&lt;/a&gt;. Facebook will be an ongoing problem for people who care about their privacy, because &lt;a href="http://en.wikipedia.org/wiki/Mark_Zuckerberg"&gt;Mark Zuckerberg&lt;/a&gt; obviously doesn't.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-8910597339282241394?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/8910597339282241394/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=8910597339282241394' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/8910597339282241394'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/8910597339282241394'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/04/some-us-senators-chastise-facebook.html' title='Some US Senators Chastise Facebook'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-2061103011646965191</id><published>2010-04-26T12:59:00.002-02:30</published><updated>2010-04-26T12:59:23.207-02:30</updated><title type='text'>McAfee Pays Home Users for Damages</title><content type='html'>&lt;a href="http://us.mcafee.com/en-us/landingpages/np5959.asp"&gt;McAfee is offering to pay for damages&lt;/a&gt; for home users affected by the bad update they released recently.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-2061103011646965191?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/2061103011646965191/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=2061103011646965191' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/2061103011646965191'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/2061103011646965191'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/04/mcafee-pays-home-users-for-damages.html' title='McAfee Pays Home Users for Damages'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-437431944995715664</id><published>2010-04-22T14:37:00.000-02:30</published><updated>2010-04-22T14:37:28.922-02:30</updated><title type='text'>Static Analysis</title><content type='html'>As my wife calls them, there's a "how we done it good" article on &lt;a href="http://www.drdobbs.com/tools/224600102"&gt;static code analysis tools&lt;/a&gt; over at Dr. Dobb's.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-437431944995715664?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/437431944995715664/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=437431944995715664' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/437431944995715664'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/437431944995715664'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/04/static-analysis.html' title='Static Analysis'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-1259793072900707609</id><published>2010-04-21T10:03:00.002-02:30</published><updated>2010-04-21T10:04:18.427-02:30</updated><title type='text'>Government Services</title><content type='html'>This &lt;a href="http://www.cbc.ca/technology/story/2010/04/20/attorney-general-report-100420.html"&gt;CBC article&lt;/a&gt; highlights some of the points from Chapter 1 of of the &lt;a href="http://www.oag-bvg.gc.ca/internet/English/parl_oag_201004_e_33704.html"&gt;Auditor General's Spring 2010 Report&lt;/a&gt;. I still have to read the report, but according to the CBC, old hardware and software are putting the reliability of government services at risk. So they have a legacy problem, who hasn't?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-1259793072900707609?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/1259793072900707609/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=1259793072900707609' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1259793072900707609'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1259793072900707609'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/04/government-services.html' title='Government Services'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-1722219800718150402</id><published>2010-04-06T09:55:00.000-02:30</published><updated>2010-04-06T09:55:49.486-02:30</updated><title type='text'>Fuzz Testing</title><content type='html'>&lt;a href="http://en.wikipedia.org/wiki/Fuzz_testing"&gt;Fuzz testing&lt;/a&gt; is used to test program interfaces for graceful handling of unexpected data. The interface is typically a data file format or network interface. In this article &lt;a href="http://www.computerworld.com/s/article/9174539/Microsoft_runs_fuzzing_botnet_finds_1_800_Office_bugs"&gt;Microsoft tests Office file formats&lt;/a&gt; using a botnet. The article compares it to seti@home, but I doubt finding a bug in Office is as unlikely as finding intelligent signals from space.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-1722219800718150402?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/1722219800718150402/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=1722219800718150402' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1722219800718150402'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1722219800718150402'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/04/fuzz-testing.html' title='Fuzz Testing'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-2921502782338591613</id><published>2010-03-29T10:32:00.000-02:30</published><updated>2012-01-25T00:42:14.384-03:30</updated><category scheme='http://www.blogger.com/atom/ns#' term='malware'/><title type='text'>Rogue Antivirus</title><content type='html'>A computer of a friend of mine was infected by the &lt;a href="http://en.wikipedia.org/wiki/Rogue_antivirus"&gt;rogue antivirus&lt;/a&gt; program, "&lt;a href="http://en.wikipedia.org/wiki/Security_Tool"&gt;Security Tool&lt;/a&gt;" over the weekend. This program hijacks the computer preventing it from running other programs, in particular it prevents the running of the process manager or the antivirus program. It masquerades as a legitimate antivirus program telling you the computer has X, Y or Z virus. &lt;b&gt;And here is where the SCAM comes in, it then tells you to enter your credit card information to upgrade to the professional version so that it can remove the detected viruses.&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;Luckily this was not a hard problem to fix. I rebooted with a &lt;a href="http://www.knoppix.net/"&gt;Knoppix Live CD&lt;/a&gt;, found the shortcut in the "Startup" folder, deleted the evil application, and rebooted back to Windows.&lt;br /&gt;&lt;br /&gt;What can be done about this kind of problem?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-2921502782338591613?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/2921502782338591613/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=2921502782338591613' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/2921502782338591613'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/2921502782338591613'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/03/rogue-antivirus.html' title='Rogue Antivirus'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-9202815344918951377</id><published>2010-03-14T12:47:00.000-02:30</published><updated>2010-03-14T12:47:06.075-02:30</updated><title type='text'>Software Executes on Real Devices, not Abstract Ones</title><content type='html'>This article, by a Mars Pathfinder engineer, about the recent &lt;a href="http://www.latimes.com/news/opinion/opinionla/la-oew-cummings12-2010mar12,0,2595172.story"&gt;Toyota problems&lt;/a&gt; has a great example of when testing the impossible paid off.&lt;br /&gt;&lt;br /&gt;During Pathfinder development one particular test tested a logical impossibility; the return value of a function that always returned an even number was tested for evenness. Seemingly beyond reason, one time the test failed. It was later determined that an interrupt had reset some register flags so that when the code resumed it calculated the wrong thing. The lesson here is that software executes on real-world machines, not abstract ones, anything can happen.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-9202815344918951377?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/9202815344918951377/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=9202815344918951377' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/9202815344918951377'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/9202815344918951377'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/03/software-executes-on-real-devices-not.html' title='Software Executes on Real Devices, not Abstract Ones'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-1375470731216040908</id><published>2010-03-03T11:21:00.001-03:30</published><updated>2012-01-25T00:43:08.479-03:30</updated><category scheme='http://www.blogger.com/atom/ns#' term='malware'/><category scheme='http://www.blogger.com/atom/ns#' term='law'/><title type='text'>Botnet Badguys Arrested</title><content type='html'>Spanish police are  &lt;a href="http://www.reuters.com/article/idUSTRE6214ST20100303"&gt;reporting&lt;/a&gt; the arrest of three people responsible for the 13 million node Mariposa botnet. Evidence in the case includes personal data from over 8 hundred thousand people.&lt;br /&gt;&lt;br /&gt;Defense Intelligence has a lot of &lt;a href="http://www.defintel.com/mariposa.shtml"&gt;interesting reading&lt;/a&gt; on this botnet.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-1375470731216040908?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/1375470731216040908/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=1375470731216040908' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1375470731216040908'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1375470731216040908'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/03/spanish-police-are-reporting-arrest-of.html' title='Botnet Badguys Arrested'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-3962245483361614319</id><published>2010-03-02T11:05:00.000-03:30</published><updated>2012-01-25T00:41:32.910-03:30</updated><category scheme='http://www.blogger.com/atom/ns#' term='bugs'/><title type='text'>Anybody Know what Time it is?</title><content type='html'>Leap year calculations are simple and correct libraries exist. Why, then, is the Sony PlayStation 3 exhibiting &lt;a href="http://www.cbc.ca/technology/story/2010/03/02/tech-sony-playstation.html"&gt;a leap year bug&lt;/a&gt;?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-3962245483361614319?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/3962245483361614319/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=3962245483361614319' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3962245483361614319'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3962245483361614319'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/03/anybody-know-what-time-it-is.html' title='Anybody Know what Time it is?'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-8002357670229943014</id><published>2010-02-19T16:53:00.001-03:30</published><updated>2010-02-19T16:54:18.132-03:30</updated><title type='text'>Writing Security into the Contract</title><content type='html'>The &lt;a href="http://www.sans.org/appseccontract/"&gt;Application Security Procurement Language&lt;/a&gt; from the SANS Institute aims to enable buyers of custom software to make code writers responsible for checking the code and for fixing security flaws before software is delivered. The introduction includes a link to CWE's &lt;a href="http://cwe.mitre.org/top25/"&gt;Top 25 Most Dangerous Programming Errors&lt;/a&gt; for 2010.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-8002357670229943014?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/8002357670229943014/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=8002357670229943014' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/8002357670229943014'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/8002357670229943014'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/02/application-security-procurement.html' title='Writing Security into the Contract'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-1500566989623324151</id><published>2010-01-20T10:47:00.000-03:30</published><updated>2010-01-20T10:47:32.543-03:30</updated><title type='text'>Open-PC</title><content type='html'>A bit off topic, but I thought this looked interesting. The &lt;a href="http://open-pc.com/"&gt;Open-PC group&lt;/a&gt; are specing PCs around supported and open hardware. In this context "supported and open" means there is enough documentation to write a Linux driver.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-1500566989623324151?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/1500566989623324151/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=1500566989623324151' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1500566989623324151'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/1500566989623324151'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/01/open-pc.html' title='Open-PC'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-2948359979246210681</id><published>2010-01-18T11:32:00.001-03:30</published><updated>2010-01-18T11:33:33.820-03:30</updated><title type='text'>German government warns against using Microsoft Internet Explorer</title><content type='html'>The government of the largest (most important) software market in Western Europe, &lt;a href="http://news.bbc.co.uk/2/hi/technology/8463516.stm"&gt;Germany, is advising its citizens against using Microsoft Internet Explorer&lt;/a&gt; (MS IE). The reason has to do with the recent news of Google China being the target of corporate espionage allegedly by the Chinese government.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-2948359979246210681?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/2948359979246210681/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=2948359979246210681' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/2948359979246210681'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/2948359979246210681'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2010/01/german-government-warns-against-using.html' title='German government warns against using Microsoft Internet Explorer'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-666451773749362935</id><published>2009-12-24T10:32:00.000-03:30</published><updated>2012-01-25T00:43:52.610-03:30</updated><category scheme='http://www.blogger.com/atom/ns#' term='malware'/><title type='text'>Clickjacking</title><content type='html'>&lt;a href="http://www.sectheory.com/clickjacking.htm"&gt;Clickjacking&lt;/a&gt; is yet another way to be attacked on the web.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-666451773749362935?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/666451773749362935/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=666451773749362935' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/666451773749362935'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/666451773749362935'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2009/12/clickjacking.html' title='Clickjacking'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-6841142210995774461</id><published>2009-12-17T16:58:00.000-03:30</published><updated>2009-12-17T16:58:43.385-03:30</updated><title type='text'>On-line Security</title><content type='html'>&lt;a href="http://www.messagelabs.com/mlireport/2009MLIAnnualReport_Final_PrintResolution.pdf"&gt;MessageLabs Intelligence: 2009 Annual Security Report&lt;/a&gt; is a very long report about on-line security in 2009. It is mostly concerned with the scope of the problem, but it also describes the most popular types of attack in a basic way.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-6841142210995774461?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/6841142210995774461/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=6841142210995774461' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/6841142210995774461'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/6841142210995774461'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2009/12/on-line-security.html' title='On-line Security'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-3420850078301515910</id><published>2009-12-17T11:24:00.000-03:30</published><updated>2009-12-17T11:24:15.420-03:30</updated><title type='text'>Automated to Death</title><content type='html'>&lt;a href="http://spectrum.ieee.org/computing/software/automated-to-death/0"&gt;Automated to Death&lt;/a&gt; in IEEE Spectrum is not strictly about seeking better software in the sense that I normally think about it, but it is a very interesting read.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-3420850078301515910?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/3420850078301515910/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=3420850078301515910' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3420850078301515910'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3420850078301515910'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2009/12/automated-to-death.html' title='Automated to Death'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-7889841021956171197</id><published>2009-12-16T17:54:00.000-03:30</published><updated>2009-12-16T17:54:45.264-03:30</updated><title type='text'>Commercial Software Should Be Judged by the Same Standards as Other Commercial Products</title><content type='html'>This &lt;a href="http://games.slashdot.org/story/09/12/16/0934206/Are-Complex-Games-Doomed-To-Have-Buggy-Releases"&gt;Slashdot story&lt;/a&gt; links to an article containing the following quote from &lt;a href="http://en.wikipedia.org/wiki/Andrew_S._Tanenbaum"&gt;Prof. Tanenbaum&lt;/a&gt;:&lt;br /&gt;&lt;br /&gt; &lt;blockquote&gt;“I think the idea that commercial software be judged by the same standards as other commercial products is not so crazy,” he says. “Cars, TVs, and telephones are all expected to work, and they are full of software. Why not standalone software? I think such legislation would put software makers under pressure to first make sure their software works, then worry about more bells and whistles.”&lt;/blockquote&gt;&lt;br /&gt;Hear, hear.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-7889841021956171197?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/7889841021956171197/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=7889841021956171197' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/7889841021956171197'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/7889841021956171197'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2009/12/commercial-software-should-be-judged-by.html' title='Commercial Software Should Be Judged by the Same Standards as Other Commercial Products'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-3596245922167832500</id><published>2008-09-30T17:36:00.004-02:30</published><updated>2008-09-30T17:58:09.066-02:30</updated><title type='text'>Lisp in C</title><content type='html'>As an exercise, I implemented Paul Graham's, "&lt;a href="http://www.paulgraham.com/rootsoflisp.html"&gt;The Roots of Lisp&lt;/a&gt;" in C. The result is available on &lt;a href="http://code.google.com/p/trol/"&gt;Google Code&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Two comments I've received so far are:&lt;ol&gt;&lt;li&gt;Why C? Write in lisp if you want to learn lisp.&lt;/li&gt;&lt;li&gt;Why not go the other way, a C interpreter in lisp?&lt;/li&gt;&lt;/ol&gt;Of course these are both possible, and certainly, the best way to learn a language is to use it.&lt;br /&gt;&lt;br /&gt;However, writing lisp interpreters in lisp hides a few details. For example, garbage collection does not even need mentioning because the underlying lisp handles it. Another example, is the interpretation of truth, a lisp implementation would not have to explicitly map the interpreted lisp's truth to the implementation languages truth. Finally, cond written in terms of cond does not have to decide what to return if none of the cases are true, it can be implicit. And there are other examples. By writing the interpreter in C, some of these details that I might have missed were made obvious.&lt;br /&gt;&lt;br /&gt;Writing a C interpreter in lisp sounds like a fun project, but it also sounds like a bigger project. Maybe I'll take that on next, maybe I'll start by writing, "The Roots of C."&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-3596245922167832500?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/3596245922167832500/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=3596245922167832500' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3596245922167832500'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/3596245922167832500'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2008/09/lisp-in-c.html' title='Lisp in C'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-116045897322744531</id><published>2006-10-10T03:12:00.000-02:30</published><updated>2012-01-25T00:34:34.332-03:30</updated><category scheme='http://www.blogger.com/atom/ns#' term='humour'/><title type='text'>vi</title><content type='html'>&lt;p&gt;My vote in the great &lt;em&gt;vi&lt;/em&gt; versus &lt;em&gt;emacs&lt;/em&gt; debate:&lt;/p&gt;&lt;a href="http://photos1.blogger.com/blogger/76/3967/1600/visa_vi.png"&gt;&lt;img style="cursor:pointer; cursor:hand;" src="http://photos1.blogger.com/blogger/76/3967/320/visa_vi.png" border="0" alt="vi. It's everywhere you want to be." /&gt;&lt;/a&gt;&lt;p&gt;I'll leave someone else to do: &lt;cite&gt;For everything else there's emacs.&lt;/cite&gt;&lt;/p&gt;&lt;p&gt;PS. If you would like this graphic as encapsulated postscript, perhaps to print on a T-shirt, drop me a line.&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-116045897322744531?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/116045897322744531/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=116045897322744531' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/116045897322744531'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/116045897322744531'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2006/10/vi.html' title='vi'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-35618625.post-116045838536546800</id><published>2006-10-10T03:02:00.000-02:30</published><updated>2006-10-11T03:02:40.153-02:30</updated><title type='text'>Nelder-Mead Downhill Simplex Method</title><content type='html'>&lt;p&gt;A stylistic review the &lt;a href="http://www.nrbook.com/a/bookcpdf/c10-4.pdf"&gt;Nelder-Mead Downhill Simplex Method&lt;/a&gt; as presented in section 10.4 of "Numerical Recipes in C," 2nd ed., 2002.&lt;/p&gt;&lt;p&gt;Studying the code presented in Numerical Recipes did reveal a few things. First of all, the good news, is that I did not find any functional bugs. As near as I can tell, the algorithm works as advertised.&lt;/p&gt;&lt;p&gt;However, I still found several points to complain about. Since the code was designed this way, I won't mention the fact that their array indexing starts at 1, which will confuse all native C programmers. (Ok, I guess I will mention it. Tsk, tsk.) (Not that C programmers don't deserve what they get anyway.) Instead, I will talk about some of the other things I saw.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Sorting&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The first problem is the use of the comma operator. Happily, they do not get it wrong the way most programmers get it wrong. That is, at least it works the way the author intended it to. In this case the author got it wrong by using it when it wasn't needed. (It is almost never needed.) The code I'm talking about is the code to determine &lt;code&gt;ilo&lt;/code&gt;, &lt;code&gt;ihi&lt;/code&gt; and &lt;code&gt;inhi&lt;/code&gt;. This section contains several weaknesses, so I'll repeat it here (with my own spacing).&lt;/p&gt;&lt;p&gt;&lt;code&gt;&lt;pre&gt; 1  /*&lt;br /&gt; 2          First we must determine which point is the&lt;br /&gt; 3          highest (worst), next-highest, and lowest&lt;br /&gt; 4          (best), by looping over the points in the&lt;br /&gt; 5          simplex.&lt;br /&gt; 6  */&lt;br /&gt; 7  ilo = 1;&lt;br /&gt; 8  ihi = y[1] &gt; y[2] ? ( inhi = 2 , 1 ) : ( inhi = 1 , 2 );&lt;br /&gt; 9  for ( i = 1; i &lt;= mpts; i++ ) {&lt;br /&gt;10          if ( y[i] &lt;= y[ilo] ) ilo = i;&lt;br /&gt;11          if ( y[i] &gt; y[ihi] ) {&lt;br /&gt;12                  inhi = ihi;&lt;br /&gt;13                  ihi = i;&lt;br /&gt;14          }&lt;br /&gt;15          else if ( y[i] &gt; y[inhi] &amp;&amp; i != ihi ) inhi = i;&lt;br /&gt;16  }&lt;/pre&gt;&lt;/code&gt;&lt;/p&gt;&lt;p&gt;First, note that &lt;code&gt;mpts&lt;/code&gt; is guaranteed to be at least 2 since we require the objective function to take at least one argument, otherwise what is the point? Therefore, since indexing starts at 1 (yech!), &lt;code&gt;y[1]&lt;/code&gt; and &lt;code&gt;y[2]&lt;/code&gt; are valid.&lt;/p&gt;&lt;p&gt;On line 8, use of the ternary operator and the comma operators ensure that after initialization, &lt;code&gt;y[ihi] &gt;= y[inhi]&lt;/code&gt;. However, this effort turns out to be unnecessary because the subsequent for-loop is sufficient to make sure that the indices have the correct values. If the loop started at &lt;code&gt;i = 2&lt;/code&gt;, then it would matter, but it doesn't, so it doesn't. What does matter, and which should be documented, is that &lt;code&gt;ihi != inhi&lt;/code&gt;. Because of the simplex algorithm design this matters later on, and if it is not enforced by the initialization, the loop is not guaranteed to straighten it out, consider &lt;code&gt;mpts == 2 &amp;&amp; y[1] == y[2]&lt;/code&gt;. Therefore, it makes sense to simply write &lt;code&gt;inhi = 1; ihi = 2;&lt;/code&gt; and let the for-loop sort it out.&lt;/p&gt;&lt;p&gt;Ignoring the silly indexing, the only change on line 9 is that &lt;code&gt;i++&lt;/code&gt; should be &lt;code&gt;++i&lt;/code&gt;. I can hear your shock from here. :) There is a very strong argument against this change, and that is that C programmers are used to writing it this way. Writing anything else means that native C programmers have to think about it, and it is obviously not worth thinking about (in C). I have two arguments for making this change. The first is that, as a programmer, you should say what you mean. If you mean increment &lt;code&gt;i&lt;/code&gt;, then write &lt;code&gt;++i&lt;/code&gt;. If you mean copy &lt;code&gt;i&lt;/code&gt;, increment &lt;code&gt;i&lt;/code&gt; and get back the copy of &lt;code&gt;i&lt;/code&gt;, then write &lt;code&gt;i++&lt;/code&gt;. The second reason, related to the first, is that in C++ these two operations can be wildly different because they can be user-defined. This prevents the compiler from replacing one form with the other if it detects the return value is not used because it can be hard to determine if there may be side-effects that will be lost. The C compiler does not have this problem because it knows exactly what the increment operators do. That is, because &lt;code&gt;i++&lt;/code&gt; does more work, there may be an inefficiency found in C++ not found in C because the C++ compiler may not be able to easily call &lt;code&gt;++i&lt;/code&gt; instead. But the main reason is that you should say what you mean.&lt;/p&gt;&lt;p&gt;Line 10 should be &lt;code&gt;y[i] &lt; y[ilo]&lt;/code&gt; rather than &lt;code&gt;y[i] &lt;= y[ilo]&lt;/code&gt;. This is simply because there is no point in moving ilo unless the new point is actually lower. And again, in C++ there could be an efficiency gain. Imagine if &lt;code&gt;y&lt;/code&gt; were an array of type &lt;code&gt;complex&lt;/code&gt; and that these operators were designed to compare magnitudes. Then &lt;code&gt;operator&lt;=()&lt;/code&gt; might be equivalent to &lt;code&gt;y[i] &lt; y[ilo] || y[i] == y[ilo]&lt;/code&gt;, where both &lt;code&gt;&lt;&lt;/code&gt; and &lt;code&gt;==&lt;/code&gt; result in function calls that each calculate magnitudes for &lt;code&gt;y[i]&lt;/code&gt; and &lt;code&gt;y[ilo]&lt;/code&gt;. The result being that similar work is done twice.&lt;/p&gt;&lt;p&gt;Line 11 should be &lt;code&gt;else if ( y[ihi] &lt; y[i] )&lt;/code&gt;. I changed the ordering and used &lt;code&gt;&lt;&lt;/code&gt; instead of &lt;code&gt;&gt;&lt;/code&gt; for reasons related to the discussion above. In C++ it is conventional to implement &lt;code&gt;&lt;&lt;/code&gt; and &lt;code&gt;==&lt;/code&gt; and to implement all other operators in terms of them, unless there is a good reason not to. Therefore, it is safer, from an efficiency point of view, to restrict which operators you use. The reason for the else is maybe even more subtle. It turns out that you can show by induction that it is only necessary to execute one of these if conditions, if any, on each pass. Therefore, the else gives us a slight efficiency gain. It can also be shown that it reduces the &lt;a href="http://en.wikipedia.org/wiki/Cyclomatic_complexity"&gt;cyclomatic complexity&lt;/a&gt; of the for-loop body from 6 to 4.&lt;/p&gt;&lt;p&gt;The final change, on line 15, is to use &lt; rather than &gt;, for reasons already discussed.&lt;/p&gt;&lt;p&gt;The best changes from a C point of view were the initialisation of &lt;code&gt;ihi&lt;/code&gt; and &lt;code&gt;inhi&lt;/code&gt;, a change from &lt;code&gt;&lt;=&lt;/code&gt; to &lt;code&gt;&lt;&lt;/code&gt;, and the introduction of an &lt;code&gt;else&lt;/code&gt;. From a C++ point of view, the changes involved more careful choice of operators. For the code as given, it probably does not matter, however you want to have good habits.&lt;/p&gt;&lt;p&gt;I should point out that searching and sorting algorithms are notoriously hard to get exactly right. In fact, there are likely still flaws and points that could be debated.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Reflecting the High Point&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;Read the comments on lines 3 and 9 in the following block of code carefully and compare them to the if-conditions that they follow.&lt;/p&gt;&lt;p&gt;&lt;code&gt;&lt;pre&gt; 1  ytry = amotry( p, y, psum, ndim, funk, ihi, -1.0 );&lt;br /&gt; 2  if ( ytry &lt;= y[ilo] )&lt;br /&gt; 3          /*&lt;br /&gt; 4                  Gives a result better than the best point, so try an&lt;br /&gt; 5                  additional extrapolation by a factor 2.&lt;br /&gt; 6          */&lt;br /&gt; 7          ytry = amotry( p, y, psum, ndim, funk, ihi, 2.0 );&lt;br /&gt; 8  else if ( ytry &gt;= y[inhi] ) {&lt;br /&gt; 9          /*&lt;br /&gt;10                  The reflected point is worse than the second-highest, so&lt;br /&gt;11                  look for an intermediate lower point, i.e., do a&lt;br /&gt;12                  one-dimensional contraction.&lt;br /&gt;13          */&lt;br /&gt;14          ysave = y[ihi];&lt;br /&gt;15          ytry = amotry( p, y, psum, ndim, funk, ihi, 0.5 );&lt;br /&gt;16          if ( ytry &gt;= ysave ) {&lt;br /&gt;17                  /*&lt;br /&gt;18                          Can't seem to get rid of that high point. Better&lt;br /&gt;19                          contract around the lowest (best) point.&lt;br /&gt;20                  */&lt;/pre&gt;&lt;/code&gt;&lt;/p&gt;&lt;p&gt;In both cases, the comment (or maybe the code) is wrong. So far my testing suggests that the code is correct and it is the comments that are wrong. This is a little unusual, it is usually easier to get the comments right and the code wrong. Incorrect comments usually indicate code that has been changed by someone who did not think to update the comments. I suppose I prefer incorrect comments over incorrect code, but I think I also prefer missing comments over incorrect comments. Incorrect comments confuse maintenance programmers because it is hard to know whether the documented behaviour or the coded behaviour is prefered. Incorrect comments are also bad because programmers who only read the comments will expect the code to behave according to the comments and may miss the bug in the associated code. &lt;a href="http://www.trolltech.com/"&gt;TrollTech&lt;/a&gt; seems to be very good at dealing with this issue. It appears that they have a policy whereby the documentaton is always correct. If code deviates from the comments, the code is re-written to match the comment.&lt;/p&gt;&lt;p&gt;In this case the comments make stronger statements than the code. The comments use the words better than and worse than, however the code only says &lt;code&gt;&lt;=&lt;/code&gt; and &lt;code&gt;&gt;=&lt;/code&gt; which are better translated as better than or the same as and worse than or the same as. The point in the first case is that the simplex reflection appears to be a move in the right direction, so move farther. The point in the second case is that the simplex reflection did not move the high point below the next-highest point, so if we stop there we are fiddling with the same point next time around.&lt;/p&gt;&lt;p&gt;In fact, by re-writing the documentation so that it is clearer that the goal is to move the highest point below the next-highest point in order to ensure progress, we can also see a slight algorithmic improvement in the code. Line 14 records the old value of &lt;code&gt;y[ihi]&lt;/code&gt; so that it can be compared to the new value returned by &lt;code&gt;amotry()&lt;/code&gt;. This is not necessary because what we really want to compare to is &lt;code&gt;y[inhi]&lt;/code&gt; as we did in the previous if-condition. Therefore, &lt;code&gt;ysave&lt;/code&gt; can be removed from the code. This change simplifies the code and makes it a little more efficient.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Contracting about the Low Point&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The final change I'll talk about involves re-using a variable for a purpose other than that for which it was intended, and doing so unnecessarily. Consider:&lt;/p&gt;&lt;p&gt;&lt;code&gt;&lt;pre&gt; 1  for ( j = 1; j &lt;= ndim; j++ )&lt;br /&gt; 2          p[i][j] = psum[j] = 0.5 * ( p[i][j] + p[ilo][j] );&lt;br /&gt; 3  y[i] = (*funk)(psum);&lt;/pre&gt;&lt;/code&gt;&lt;/p&gt;&lt;p&gt;First, there is the &lt;code&gt;j++&lt;/code&gt; which I've commented on before. Second, I do not think it is required to dereference the function pointer, &lt;code&gt;funk&lt;/code&gt; in order to call it, but it might be. But the main problem is the use of &lt;code&gt;psum&lt;/code&gt;.&lt;/p&gt;&lt;p&gt;Without more context, this looks reasonable. What if I told you that &lt;code&gt;psum&lt;/code&gt; was not used again until it is re-calculated a few lines later? In this case, I assume &lt;code&gt;psum&lt;/code&gt; is being used because the author did not want to write &lt;code&gt;y[i] = funk( p[i] )&lt;/code&gt;, but I do not see why not, and is it worth the cost of the extra assignments? More to the point, is it worth the confusion to the maintenance programmer who looks at line 3 and wonders why the objective function is being called with the simplex centroid vector, rather than one of the rows of the simplex as is usual? I think these three lines of code are simply evil.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;Summary&lt;/strong&gt;&lt;/p&gt;&lt;p&gt;The previous three sections raise what many people would consider to be nit-picky points. Afterall, the code appears to work. Even the changes that might impact efficiency will only make a small difference. From that point of view, the points are nit-picky. People will also say that by proposing nit-picky changes I risk breaking code that works. That is also true.&lt;/p&gt;&lt;p&gt;I personally do not find either of these arguments very persuasive. Correctness of functionality is not the only useful measuring stick that we can apply to code. Effectiveness of communication is also very important. Effective communication matters as much as functionality or efficiency because code has to be maintained. If some code is not observably correct, then it becomes a target for investigation when a bug is found. It is wasteful "debugging" code that is not the source of the problem. Similarly, even when code is correct it sometimes needs slight changes to support new requirements. It is wasteful verifying that the starting point is correct when it is, and it is time consuming understanding code that is not clear enough so that changes can be made safely. I believe that code that communicates effectively reduces the burden of testing. I would rather write clear code than test. As for the risk associated with making changes, you have to weigh the expected benefit against the expected cost. In general, the risk of getting a nit-picky change wrong is lower than the risk of getting a large change wrong. From this point of view, I prefer nit-picky changes. Second, while the benefit of a particular nit-picky change may be small, I think it is more important to consider the net effect over time. Small changes are a way of balancing the need for safety and the need for improvement.&lt;/p&gt;&lt;p&gt;In summary, I discussed the following improvements in the previous sections:&lt;ol&gt;&lt;li&gt;Avoid using the ternary and comma operators. In the index sorting algorithm, they can be removed. This is a good change because these operators (especially comma) are poorly understood by many programmers. It also removes some unnecessary complexity which simplifies communication.&lt;/li&gt;&lt;li&gt;Array indexing starts at 0. I did not recommend this change, because the algorithm is designed to be part of a library which behaves this way, but vector indexing should really start at 0. Starting at 1 is potentially confusing to C programmers.&lt;/li&gt;&lt;li&gt;Call &lt;code&gt;operator++()&lt;/code&gt; instead of &lt;code&gt;operator++(int)&lt;/code&gt;, that is, prefix instead of postfix. This change makes most sense from a C++ point of view, since it is a good C++ habit. However, it also makes sense from a say what you mean point of view.&lt;/li&gt;&lt;li&gt;Prefer &lt;code&gt;&lt;&lt;/code&gt; over other comparison operators such as &lt;code&gt;&gt;&lt;/code&gt;. This is only because of C++ operator implementation conventions.&lt;/li&gt;&lt;li&gt;Use &lt;code&gt;&lt;&lt;/code&gt; instead of &lt;code&gt;&lt;=&lt;/code&gt; in the index sorting algorithm. This is perceived as reducing the amount of unnecessary work. In fact it might not since now more if-conditions will have to be evaluated.&lt;/li&gt;&lt;li&gt;Use &lt;code&gt;else if&lt;/code&gt; instead of &lt;code&gt;if&lt;/code&gt; in the index sorting algorithm. This is good because it reduces the amount of work that the algorithm does. You can also think of this as reducing the cyclomatic complexity of this block from 6 to 4.&lt;/li&gt;&lt;li&gt;Document invariants. By documenting the importance of &lt;code&gt;ihi != inhi&lt;/code&gt;, it is safer to make changes to this code.&lt;/li&gt;&lt;li&gt;Documentation must agree with code. It is important that code and documentation agree so that there is no ambiguiity over what code should actually be doing.&lt;/li&gt;&lt;li&gt;Document why rather than what or how. By documenting the purpose of the code, the comments are complementary rather than repetative. In the particular case discussed regarding the results of &lt;code&gt;amotry()&lt;/code&gt;, better comments lead to better code.&lt;/li&gt;&lt;li&gt;Remove extra variables. Extra variables add to what a programmer has to keep track of while trying to understand an algorithm. By removing &lt;code&gt;ysave&lt;/code&gt;, there is that much less to worry about.&lt;/li&gt;&lt;li&gt;Do not re-use variables. The re-use of &lt;code&gt;psum&lt;/code&gt; was simply evil. Re-using a variable because it has the same type is like saying any verb will do. It is confusing because the wrong meaning is conveyed. In this case it is even worse because it results in extra assignments and doesn't even save you any writing (which is the usual reason for doing it).&lt;/li&gt;&lt;/ol&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/35618625-116045838536546800?l=aburry.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://aburry.blogspot.com/feeds/116045838536546800/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=35618625&amp;postID=116045838536546800' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/116045838536546800'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/35618625/posts/default/116045838536546800'/><link rel='alternate' type='text/html' href='http://aburry.blogspot.com/2006/10/nelder-mead-downhill-simplex-method.html' title='Nelder-Mead Downhill Simplex Method'/><author><name>Adam Burry</name><uri>https://profiles.google.com/110720943291800673011</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='//lh4.googleusercontent.com/-3kyQkCdtc1k/AAAAAAAAAAI/AAAAAAAAAEE/80u25gg15TI/s512-c/photo.jpg'/></author><thr:total>0</thr:total></entry></feed>
