{"id":4,"date":"2015-11-30T22:31:18","date_gmt":"2015-11-30T22:31:18","guid":{"rendered":"http:\/\/eleganthack.net\/blog\/?p=4"},"modified":"2023-01-16T22:56:29","modified_gmt":"2023-01-16T22:56:29","slug":"installing-linux-on-a-compact-flash-card","status":"publish","type":"post","link":"https:\/\/eleganthack.net\/blog\/?p=4","title":{"rendered":"Installing Linux on a Compact Flash Card"},"content":{"rendered":"\n<p>I tend to favor purpose-built appliances &#8212; devices that &#8220;do one thing, and do it well.&#8221;&nbsp;&nbsp;So I have a few Linux-based appliances that live in closets and under desks, humming and blinking away. &nbsp;Most of these boot from flash disks, and have been for some time.<\/p>\n\n\n\n<p>Here&#8217;s an old entry from my notes for the retro crowd, when IDE and Compact Flash were relevant tech.&nbsp; Enjoy!<\/p>\n\n\n\n<!--more-->\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<p>Compact Flash cards are electrically and logically compatible with ATA (IDE), so if you&#8217;re using a motherboard that supports IDE, a simple passive adapter is all that&#8217;s needed to make it appear as an ordinary hard disk to Linux. Usually.<\/p>\n\n\n\n<p>In reality, the card&#8217;s support for UDMA modes can vary, and not all CF-to-IDE adapters properly patch the pins on the cable to the necessary pins on the card. &nbsp;As a result, sometimes UDMA operations&nbsp;fail, causing&nbsp;a flurry of spurious error messages and painfully slow I\/O.<\/p>\n\n\n\n<p>There are a few ways to fix this, with varying degrees of ease and collateral damage:<\/p>\n\n\n\n<ol>\n<li><p>Disable UDMA for that device in the BIOS.&nbsp; Or use a card that does not (attempt to) support UDMA. &nbsp;Linux should recognize the lack of hardware support and disable DMA for that device. Note: <em>Should<\/em>.<\/p><\/li>\n\n\n\n<li><p>If you&#8217;re using the legacy IDE kernel drivers (that is, IDE devices are enumerated as <strong>\/dev\/hd<em>x<\/em><\/strong>), add the <strong>ide=nodma<\/strong> option to the kernel boot parameters.<\/p>\n<p>This is kind of a &#8216;big hammer&#8217; approach, and will disable DMA for <em>all<\/em> IDE devices, increasing CPU overhead and thus reducing performance. &nbsp;So if you have other IDE devices, this is probably not your first pick.<\/p><\/li>\n\n\n\n<li><p>If your kernel has a (more recent, but still old) IDE driver, it may support granular (per-channel, or better yet, per-device) options.<\/p>\n<p>Try <strong>ide_core.nodma=<em>x<\/em>.<em>y<\/em><\/strong>, where <em>x<\/em> is the IDE channel, and <em>y<\/em> is the device on that channel, both starting at 0.<\/p>\n<p>I.e., you would use <strong>0.0<\/strong> for primary master, <strong>0.1<\/strong> for primary slave, or <strong>1.1<\/strong> for secondary slave.<\/p><\/li>\n\n\n\n<li><p>If you&#8217;re using the <strong>libata<\/strong> kernel drivers (which enumerates all disks as <strong>\/dev\/sd<em>x<\/em><\/strong> regardless of type) you would instead use <strong>libata.dma=<em>x<\/em><\/strong>.<\/p>\n<p>The value <em>x<\/em> is a bitmapped flag, where:<\/p>\n<ul class=\"mini\"><li>0 disables all DMA<\/li><li>1 enables DMA for PATA and SATA hard disks<\/li><li>2 enables DMA for CD-ROMs<\/li><li>4 enables DMA for Compact Flash cards.<\/li><\/ul>\n<p>Thus, a value of <strong>3<\/strong> (that is, 1 + 2) will enable DMA for hard disks and CD-ROMs, but not Compact Flash cards. &nbsp;Exactly what you want.<\/p><\/li>\n\n\n\n<li><p>Finally, if you&#8217;re really hard core, find the DMA blacklist in your kernel sources and manually add your device&#8217;s ID to the list.<\/p><\/li>\n<\/ol>\n\n\n\n<p>For <strong>libata<\/strong>, this can be found in&nbsp;<strong>\/usr\/src\/linux\/drivers\/ata\/libata-core.c<\/strong>.<\/p>\n\n\n\n<p>Look for the array definition below, and add a line like the one&nbsp;shown:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">static const struct ata_blacklist_entry ata_device_blacklist [] = {<br>...<br>{ \"BIOS CF ID Goes Here\", NULL, ATA_HORKAGE_NODMA },<br>...<br>}<\/pre>\n\n\n\n<p>You&#8217;ll need the&nbsp;<em>exact<\/em> ID your card uses (the one that shows up at boot time, in the BIOS, or from hdparm, etc.), then look around at similar entries to make sure you&#8217;re following the pattern.<\/p>\n\n\n\n<p>Finally, recompile your kernel, reboot, and see if that does the trick. &nbsp;If not, check the ID &#8212; it may be padded with spaces, for example.<\/p>\n\n\n\n<p>In reality, given the declining popularity of Compact Flash, there are probably better options. You can also find flash modules that plug in to the IDE or SATA port directly, although they&#8217;re relatively rare and usually designed for the industrial market, you&#8217;ll pay more for the novelty.<\/p>\n\n\n\n<p>So why bother? I dunno. Because you can, I guess.<\/p>\n\n\n\n<h2>Coping with frequent writes<\/h2>\n\n\n\n<p>Flash memory, of course, has limited write cycles, so it helps to manage the services that write to disk frequently &#8212; particularly syslog.<\/p>\n\n\n\n<p>The easiest way to do this, if you have a little extra memory, is to set up a RAM disk and log there:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">mount -t tmpfs -o size=100m tmpfs \/var\/log<\/pre>\n\n\n\n<p>Of course, you&#8217;ll probably want to add this to <strong>\/etc\/fstab<\/strong> so it&#8217;s there when the syslog daemon starts. And adjust the size parameter to taste.<\/p>\n\n\n\n<p>As the name implies, the contents won&#8217;t survive a reboot. If you care, you can configure the syslog daemon, or <strong>logrotate<\/strong>, to copy them to persistent storage at some point.<\/p>\n\n\n\n<p>Alternatively, forward syslog events to an external host instead. If this isn&#8217;t for home use, definitely do that. That&#8217;s another article though.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>I tend to favor purpose-built appliances &#8212; devices that &#8220;do one thing, and do it well.&#8221;&nbsp;&nbsp;So I have a few Linux-based appliances that live in closets and under desks, humming and blinking away. &nbsp;Most of these boot from flash disks, and have been for some time. Here&#8217;s an old entry from my notes for the&#8230;<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"inline_featured_image":false,"_kad_post_transparent":"","_kad_post_title":"","_kad_post_layout":"","_kad_post_sidebar_id":"","_kad_post_content_style":"","_kad_post_vertical_padding":"","_kad_post_feature":"","_kad_post_feature_position":"","_kad_post_header":false,"_kad_post_footer":false},"categories":[22,2,21],"tags":[3,23],"_links":{"self":[{"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=\/wp\/v2\/posts\/4"}],"collection":[{"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=4"}],"version-history":[{"count":14,"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=\/wp\/v2\/posts\/4\/revisions"}],"predecessor-version":[{"id":208,"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=\/wp\/v2\/posts\/4\/revisions\/208"}],"wp:attachment":[{"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=4"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=4"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/eleganthack.net\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=4"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}