a:4:{s:7:"#markup";O:25:"Drupal\Core\Render\Markup":1:{s:9:"*string";s:294831:"<?xml version="1.0" encoding="utf-8" ?>
<rss version="2.0" xml:base="https://yaffs.net/rss.xml" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:foaf="http://xmlns.com/foaf/0.1/" xmlns:og="http://ogp.me/ns#" xmlns:rdfs="http://www.w3.org/2000/01/rdf-schema#" xmlns:schema="http://schema.org/" xmlns:sioc="http://rdfs.org/sioc/ns#" xmlns:sioct="http://rdfs.org/sioc/types#" xmlns:skos="http://www.w3.org/2004/02/skos/core#" xmlns:xsd="http://www.w3.org/2001/XMLSchema#">
  <channel>
    <title>Yaffs - A Flash File System for embedded use - A Flash file system for embedded use</title>
    <link>https://yaffs.net/rss.xml</link>
    <description></description>
    <language>en</language>
    
    <item>
  <title>YAFFS Debugging</title>
  <link>https://yaffs.net/yaffs-debugging</link>
  <description>&lt;span property=&quot;schema:name&quot;&gt;YAFFS Debugging&lt;/span&gt;
&lt;span rel=&quot;schema:author&quot;&gt;&lt;span lang=&quot;&quot; about=&quot;/user/wookey&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Wookey&lt;/span&gt;&lt;/span&gt;
&lt;span property=&quot;schema:dateCreated&quot; content=&quot;2006-09-15T21:32:13+00:00&quot;&gt;15 September, 2006 - 10:32pm&lt;/span&gt;

            &lt;div property=&quot;schema:text&quot; class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;
&lt;h1&gt;How to control debugging in yaffs&lt;/h1&gt;
&lt;p&gt;YAFFS provides a debugging mechanism which can be controlled at runtime if you have access to /proc, normally via a shell. If you need to trace things before you get to a shell, then you can set default trace options at compile time.&lt;/p&gt;
&lt;h2&gt;Available Trace Flags&lt;/h2&gt;
&lt;table&gt;
&lt;tr&gt;
 &lt;th&gt;name&lt;/th&gt;
 &lt;th&gt;C #define&lt;/th&gt;
 &lt;th&gt;bitmask value&lt;/th&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;error &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_ERROR &lt;/td&gt;
 &lt;td&gt;0x00000001&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;os &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_OS &lt;/td&gt;
 &lt;td&gt;0x00000002&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;allocate &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_ALLOCATE &lt;/td&gt;
 &lt;td&gt;0x00000004&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;scan &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_SCAN &lt;/td&gt;
 &lt;td&gt;0x00000008&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;bad_blocks &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_BAD_BLOCKS &lt;/td&gt;
 &lt;td&gt;0x00000010&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;erase &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_ERASE &lt;/td&gt;
 &lt;td&gt;0x00000020&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;gc &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_GC &lt;/td&gt;
 &lt;td&gt;0x00000040&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;write &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_WRITE &lt;/td&gt;
 &lt;td&gt;0x00000080&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;tracing &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_TRACING &lt;/td&gt;
 &lt;td&gt;0x00000100&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;deletion &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_DELETION &lt;/td&gt;
 &lt;td&gt;0x00000200&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;buffers &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_BUFFERS &lt;/td&gt;
 &lt;td&gt;0x00000400&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;nandaccess &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_NANDACCESS &lt;/td&gt;
 &lt;td&gt;0x00000800&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;gc_detail &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_GC_DETAIL &lt;/td&gt;
 &lt;td&gt;0x00001000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;scan_debug &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_SCAN_DEBUG &lt;/td&gt;
 &lt;td&gt;0x00002000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;mtd &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_MTD &lt;/td&gt;
 &lt;td&gt;0x00004000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;always &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_ALWAYS &lt;/td&gt;
 &lt;td&gt;0x40000000&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
 &lt;td&gt;bug &lt;/td&gt;
 &lt;td&gt;YAFFS_TRACE_BUG &lt;/td&gt;
 &lt;td&gt;0x80000000&lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;h2&gt;Flag meanings&lt;/h2&gt;
&lt;p&gt;The flags cover possible debugging messages from various aspects of the filesystem - initial scanning, mtd interface, writing, nand access, garbage collection, OS interaction etc. Turning on everything results an awful lot of trace info, so it is usually best to just enable a few relevant flags.&lt;/p&gt;
&lt;h2&gt;Setting flags at runtime&lt;/h2&gt;
&lt;p&gt;The flags can be set or cleared by echoing the name of the flag into /proc/yaffs with a &#039;+&#039; or &#039;-&#039;:&lt;br /&gt;
&lt;code&gt;echo +os-write &amp;gt; /proc/yaffs&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;It can be set to to all or none using &#039;=&#039;, and then flags can be added or removed:&lt;br /&gt;
&lt;code&gt;echo =none+os+write &amp;gt; /proc/yaffs&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;And you can use numerical values, if you are so inclined (using standard C format):&lt;br /&gt;
&lt;code&gt;echo 0xf00001 &amp;gt; /proc/yaffs&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;So&lt;br /&gt;
&lt;code&gt;echo all &amp;gt; /proc/yaffs&lt;/code&gt;&lt;br /&gt;
will turn all tracing on&lt;/p&gt;
&lt;p&gt;&lt;b&gt;Note&lt;/b&gt; that you only see the output showing you the current trace state if the &#039;always&#039; (YAFFS_TRACE_ALWAYS) flag is set, so to see what you are doing do this:&lt;br /&gt;
&lt;code&gt;echo +always &amp;gt; /proc/yaffs&lt;/code&gt;&lt;/p&gt;
&lt;h2&gt;Setting flags at compile time&lt;/h2&gt;
&lt;p&gt;Flags can be set in the code at compile-time by setting &lt;code&gt;yaffs_traceMask&lt;/code&gt; in &lt;code&gt;yaffs_fs.c&lt;/code&gt; (add new flags to &lt;code&gt;always&lt;/code&gt; and &lt;code&gt;bad_blocks&lt;/code&gt; which are set by default)&lt;/p&gt;
&lt;/div&gt;
      </description>
  <pubDate>Fri, 15 Sep 2006 21:32:13 +0000</pubDate>
    <dc:creator>Wookey</dc:creator>
    <guid isPermaLink="false">351 at https://yaffs.net</guid>
    </item>
<item>
  <title>YAFFS: the NAND-specific flash file system - Introductory Article</title>
  <link>https://yaffs.net/archives/yaffs-nand-specific-flash-file-system-introductory-article</link>
  <description>&lt;span&gt;YAFFS: the NAND-specific flash file system - Introductory Article&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/wookey&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Wookey&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;26 July, 2006 - 2:11pm&lt;/span&gt;

            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;Written by Charles Manning - Originally published at Linuxdevices.org Sept 20th 2002
&lt;h3&gt;PHB Summary&lt;/h3&gt;
YAFFS stands for &quot;yet another flash file system&quot;(*). As far as I am aware, YAFFS is the only file system, under any operating system, that has been designed specifically for use with NAND flash. YAFFS is thus designed to work within the constraints of, and exploit the features of, NAND flash to maximise performance. YAFFS uses journaling, error correction and verification techniques tuned to the way NAND typically fails, to enhance robustness. The result is a file system that exploits low-cost NAND chips and is both fast and robust. YAFFS is highly portable and runs under Linux, ucLinux and Windows CE. YAFFS is an open source project.
&lt;h3&gt;Why NAND flash?&lt;/h3&gt;
Embedded and mobile systems are increasingly using NAND flash for storage because it has various advantages over other storage technologies. As always though, life is a compromise and those advantages come with some limitations that need to be addressed to provide a robust flash file system. Hard disks are not a viable storage option for many embedded and handheld systems because they are too big, too fragile and use too much power. For some years now, people have been using common-old NOR flash for file system storage. JFFS and JFFS2 do an excellent job of this for Linux. For storage applications NOR flash is not that great because it is not very dense (ie. not much storage per chip), is costly and is slow to write. NAND flash, on the other hand, is low cost, dense and writes fast, but has other limitations. The most common consumer usage of NAND flash is on SmartMedia cards which are just NAND chips bonded to a carrier card. Consumer use of SmartMedia is driving down NAND prices while driving up densities. The standard SmartMedia file system is FAT based and is thus liable to corruptions due to power failures, crashes and other acts of demonic forces. This raises robustness concerns, particularly in embedded systems where a corrupted file system can kill the device. What&#039;s really needed is a journaling file system that is able to work around the limitations of NAND and exploit it for best performance.
&lt;h3&gt;History&lt;/h3&gt;
The lead-up to YAFFS started with an investigation into modifying the JFFS2 flash file system to work with NAND flash (**) for some Aleph One customers. It seemed reasonable that the best way to get a file system for NAND flash would be just &quot;tweaking&quot; an existing flash file system. On deeper investigation, it became apparent that designing a new file system specifically for NAND might have some benefits.
&lt;table border=&quot;1&quot; cellpadding=&quot;1&quot; style=&quot;width: 568px; border-color: #000000; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;186&quot; /&gt;&lt;col width=&quot;187&quot; /&gt;&lt;col width=&quot;186&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;NOR (typical, varies a lot)&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;NAND&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Density&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;Up to 32MB chips&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Currently 256MB and growing.&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Cost per MB&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;$1-$2&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;25c&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Access&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;Random&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Page oriented with spare area on each page. Sequential access within a page.&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Programmability&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;Can modify a single bit.&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Very limited re-programming.&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Read speed&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;50-100nS&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;10uS page &quot;seek&quot; + 50nS per byte&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Program time&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;5uS per byte&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;200uS per page&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Erasure time&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;1s per 64kB block&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;2ms per 16kB block&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Reliability&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 187px;&quot;&gt;
 &lt;p&gt;Relatively immune to corruption. No bad blocks.&lt;/p&gt;
 &lt;/td&gt;
 &lt;td style=&quot;width: 186px;&quot;&gt;
 &lt;p&gt;Needs error correction. Bad blocks marked when shipped.&lt;/p&gt;
 &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
Designing an effective flash file system is a difficult task and you need to jump through many hoops of fire to get a useful system. Although both are called &quot;Flash&quot;, NOR and NAND flash have very different properties. Thus, a flash file system that works with NOR incorporates various mechanisms that are not required for NAND, and NAND needs extra mechanisms not required for NOR. For example, garbage collection performance is largely determined by the erasure time. NOR erases very slowly and thus an effective NOR garbage collection strategy is relatively complex and limits the design options. In comparison NAND erases very quickly; thus these limitations don&#039;t apply. Another major difference is that NAND is shipped with marked bad blocks on the device, while NOR chips are shipped defect free. Thus, one expects to encounter some failures in NAND and should design accordingly. This lead me to believe that it would be worth designing a file system specifically for NAND flash, exploiting the features of NAND to simplify the design and catering to NAND specific limitations directly, rather than trying to &quot;bend&quot; NAND to work with an existing file system architecture, or vice versa. The first conceptual design for YAFFS was drawn up in late December 2001. Once the customers bought in to the idea, things progressed rapidly. The first line of code was cut in January 2002. By May 2002 we had the first publicly available CVS code. We now have at least six different companies using or experimenting with YAFFS in embedded or handheld systems. YAFFS is already very stable and is converging rapidly. We expect to see YAFFS-based products shipped before the end of the year.
&lt;h3&gt;Design approach&lt;/h3&gt;
Rather than develop and debug code inside the Linux kernel, I took the approach of developing the file system &quot;guts&quot; algorithms - the most complex part -- in a user space program. To achieve this, the code is split into four sections:
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;yaffs_guts: The file system algorithms. This code is fully portable C.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;yaffs_fs.c: Interface layer to the Linux VFS. Can be replaced with a test harness for user space developing of yaffs_guts.c&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;nand interface: wrapper layer between yaffs_guts and the NAND memory access functions. eg. calls Linux mtd layer or RAM emulation layer.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Portability functions: wrapper functions for services such as memory allocation etc.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
This modular design has provided a lot of flexibility for testing and development. A user space program and DDD is a far more rapid development environment than continually changing the Linux kernel. Also, a RAM-based NAND emulation layer provides an excellent way to debug the file system in-kernel without special hardware. A further spin-off has been that YAFFS is portable to other operating systems. For example, a port of YAFFS for Windows CE was readily achieved by writing a new wrapper layer to hook up to the WinCE file system manager and new NAND access layer. yaffs_guts.c remains 100% portable(***). YAFFS is thus likely to be easily portable to other OSs too.
&lt;h3&gt;Results&lt;/h3&gt;
Removing surplus constraints has lead to a simpler design that has improved performance and robustness as well and reduced development time. YAFFS reads and writes pretty fast. There is no significant hit due to garbage collection (ie. in most situations garbage collection overheads would not impact usage). It is difficult to give meaningful benchmarks given non-standard hardware. However herewith some results achieved on a StrongARM-based board with 128MB of NAND flash. Write speed is approx 800kB per second and read speed is approx 1.5MB per second. In a weekend stress test I wrote, triple-verified then deleted 25gigabytes of file data without a single bit of file data being corrupted. 25GB exceeds the design lifetime of most embedded or handheld devices.
&lt;h3&gt;Future&lt;/h3&gt;
Although YAFFS already performs well, there is still a lot of room for improvement. Development is continuing to enhance performance and robustness as well as add support software such as utilities, bootloader support and analysis tools. I expect to see ports to other OSs too. Increasing the user base of YAFFS is an important way to get more eyes over the code and test it under a wider set of scenarios. The YAFFS development community is growing well with good involvement from people all over the world. YAFFS is realising all the benefits open source projects hope for and will, we expect, continue to grow.
&lt;h3&gt;Resources&lt;/h3&gt;
The YAFFS project home page is &lt;a href=&quot;http://www.aleph1.co.uk/yaffs/&quot;&gt;http://www.aleph1.co.uk/yaffs/&lt;/a&gt; This provides further YAFFS documentation and instructions for GIT access and the YAFFS mailing list.
&lt;h3&gt;Footnotes:&lt;/h3&gt;
(*)The YAFFS name came from the first concept document proposing yet another flash file system. Some how that name just stuck. (**) NAND support has since been added to JFFS2 by others. The YAFFS, JFFS2 and mtd communities cooperate to provide a rich flexible set of solutions to draw from. As is the nature of open source projects, JFFS2 code was used as a reference for some parts of the YAFFS development, particularly for figuring out the VFS interface. Google for further info on JFFS2 and mtd. (***) Some features were added to the guts to enhance WinCE usage. For example, the string comparison function was made configurable to be either strcmp or scricmp because Windows file names are case insensitive.
&lt;h3&gt;Bio&lt;/h3&gt;
Charles Manning (aka The Embedded Janitor) lives near Christchurch, New Zealand, and has been developing and mopping up embedded systems for twenty years. His hobbies include fly tying and spinning wool. Charles can be reached at &lt;a href=&quot;denied:mailto:charles@aleph1.co.uk&quot;&gt;charles@aleph1.co.uk&lt;/a&gt;. &lt;/div&gt;
      </description>
  <pubDate>Wed, 26 Jul 2006 13:11:32 +0000</pubDate>
    <dc:creator>Wookey</dc:creator>
    <guid isPermaLink="false">347 at https://yaffs.net</guid>
    </item>
<item>
  <title>“Almost 15 years …never seen a failure...”</title>
  <link>https://yaffs.net/almost-15-years-never-seen-failure</link>
  <description>&lt;span&gt;“Almost 15 years …never seen a failure...”&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/admin&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Admin&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;1 September, 2017 - 1:03pm&lt;/span&gt;

            &lt;div class=&quot;field field--name-field-organisation field--type-string field--label-hidden field--item&quot;&gt;Tape Replacement Ltd&lt;/div&gt;
      
            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;&lt;p dir=&quot;ltr&quot;&gt;The DDS range of digital data storage solutions from Tape Replacement Ltd deliver a modern, solid state data storage unit designed specifically to replace out-dated magnetic tape, magneto optical, disc hard-drive units such as those used within legacy telephone switching systems. This saves companies such as telcos, and ultimately their customers, millions of dollars in upgrade costs as well as improving overall system reliability and keeping functioning equipment from being dumped in landfills.&lt;/p&gt;

&lt;p dir=&quot;ltr&quot;&gt;The storage layer is made up of two independent stacks of NAND chips, combined using a RAID-1 structure, using YAFFS to expose this to the application.&lt;/p&gt;

&lt;p dir=&quot;ltr&quot;&gt;According to Andre Renaud, Engineering Manager at Tape Replacement:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p dir=&quot;ltr&quot;&gt;“We&#039;ve been running the units for almost 15 years now, and we have never seen a failure of the underlying YAFFS/NAND storage system. YAFFS provides us with a fast, reliable storage mechanism which is especially useful given the changes in NAND technologies over the years, and the intricate technical details of their behaviour.”&lt;/p&gt;
&lt;/blockquote&gt;&lt;/div&gt;
      
      &lt;div class=&quot;field field--name-field-url field--type-link field--label-hidden field--items&quot;&gt;
              &lt;div class=&quot;field--item&quot;&gt;&lt;a href=&quot;http://www.tape-replacement.com/&quot;&gt;http://www.tape-replacement.com/&lt;/a&gt;&lt;/div&gt;
          &lt;/div&gt;
  
            &lt;div class=&quot;field field--name-field-image field--type-image field--label-hidden field--item&quot;&gt;    &lt;img srcset=&quot;/sites/default/files/styles/max_325x325/public/2017-09/tape_replacement.jpg?itok=HsMgXnI2 325w, /sites/default/files/styles/max_650x650/public/2017-09/tape_replacement.jpg?itok=cUoW-9yU 555w&quot; sizes=&quot;(min-width: 1290px) 325px, (min-width: 851px) 25vw, (min-width: 560px) 50vw, 100vw&quot; src=&quot;/sites/default/files/styles/max_325x325/public/2017-09/tape_replacement.jpg?itok=HsMgXnI2&quot; alt=&quot;Tape Replacement Ltd Logo&quot; typeof=&quot;foaf:Image&quot; class=&quot;img-responsive&quot; /&gt;


&lt;/div&gt;
      </description>
  <pubDate>Fri, 01 Sep 2017 12:03:28 +0000</pubDate>
    <dc:creator>Admin</dc:creator>
    <guid isPermaLink="false">503 at https://yaffs.net</guid>
    </item>
<item>
  <title>Yaffs in space!</title>
  <link>https://yaffs.net/yaffs-space</link>
  <description>&lt;span&gt;Yaffs in space!&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/admin&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Admin&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;1 September, 2017 - 12:59pm&lt;/span&gt;

            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;&lt;p&gt;&lt;strong&gt;NASA TESS Mission &lt;/strong&gt;This &lt;strong&gt;Transiting Exoplanet Survey Satellite (TESS)&lt;/strong&gt; will discover thousands of exoplanets in orbit around the brightest stars in the sky.&lt;/p&gt;

&lt;p&gt;It is a project regularly using our Yaffs File System to store incoming data and preserve it, in the rigours of the space environment, before sending it back to Earth.&lt;/p&gt;

&lt;p&gt;In a two-year survey of the solar neighborhood, TESS will monitor more than 200,000 stars for temporary drops in brightness caused by planetary transits. This first-ever spaceborne all-sky transit survey will identify planets ranging from Earth-sized to gas giants, around a wide range of stellar types and orbital distances. No ground-based survey can achieve this feat.&lt;/p&gt;

&lt;p&gt;Some File Systems are not robust enough to be suitable for such exacting work.&lt;/p&gt;&lt;/div&gt;
      </description>
  <pubDate>Fri, 01 Sep 2017 11:59:15 +0000</pubDate>
    <dc:creator>Admin</dc:creator>
    <guid isPermaLink="false">502 at https://yaffs.net</guid>
    </item>
<item>
  <title>Yaffs for VxWorks</title>
  <link>https://yaffs.net/documents/yaffs-vxworks</link>
  <description>&lt;span&gt;Yaffs for VxWorks&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/admin&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Admin&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;11 January, 2016 - 3:28pm&lt;/span&gt;

            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;
&lt;p&gt;The source and the definitive version of this document can be found in our git repository,&amp;nbsp;&lt;a href=&quot;http://www.aleph1.co.uk/gitweb/?p=yaffs-docs;a=tree;h=f4fcbdc9da052aa926c4bc2275547ca310eebbd8;hb=9d50c62a1c24f1b9dd00ec3eb6d0bddff0aed17d&quot;&gt;together with other Yaffs documents&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;1 Background&lt;/h2&gt;
&lt;p&gt;The purpose of this document is to describe the Yaffs-for-VxWorks wrapper as well as provide sufficient information to port Yaffs to the VxWorks BSP. This document assumes a working knowledge of VxWorks.&lt;/p&gt;
&lt;p&gt;This document does not describe the inner workings of Yaffs and a study of other Yaffs documents is recommended. Documents shown below in &lt;em&gt;italics&lt;/em&gt; are available at &lt;em&gt;&lt;a href=&quot;http://www.yaffs.net/documents&quot;&gt;http://www.yaffs.net/documents&lt;/a&gt;...&lt;/em&gt;&lt;/p&gt;
&lt;h2&gt;2 Licensing&lt;/h2&gt;
&lt;p&gt;Yaffs was originally released for Linux under the GNU Public License (GPL). Various embedded developers soon identified that Yaffs would be ideal for their applications, but were not able to use GPL based code in their systems. Aleph One Ltd has alternative licensing arrangements to support such applications.&lt;/p&gt;
&lt;p&gt;Since VxWorks is proprietary code that is incompatible with GPL, alternative licensing arrangements must be sought to use Yaffs with VxWorks or most other embedded RTOSs.&lt;/p&gt;
&lt;h2&gt;3 What are Yaffs and Yaffs Direct Interface?&lt;/h2&gt;
&lt;p&gt;Yaffs stands for Yet Another Flash File System and was the first file system designed from the ground up for NAND flash storage.&lt;/p&gt;
&lt;p&gt;In 2002 Aleph One set out to identify file system options for using NAND Flash as a file system. Various file systems available at the time were evaluated and all were found lacking in one way or another. The need for a suitable NAND storage file system was identified and Yaffs was designed to fill that need.&lt;/p&gt;
&lt;p&gt;Although Yaffs was originally designed for NAND flash, it has been used successfully with NOR flash systems and even as a RAM file system. This allows high reliability file systems to be constructed using NOR flash, with a future migration path to NAND flash for higher density and performance.&lt;/p&gt;
&lt;p&gt;Yaffs was originally designed for use with the Linux operating system, but was designed in a very modular way. The operating-system-specific code was kept separate from the main Yaffs file system code. This allows Yaffs to be ported quite cleanly to other operating systems through operating system personality modules. One such personality module is the Yaffs Direct Interface (YDI) which allows Yaffs to be simply integrated with embedded systems, with or without an RTOS. See &lt;a href=&quot;http://www.yaffs.net/documents/yaffs-direct-interface&quot;&gt;http://www.yaffs.net/documents/yaffs-direct-interface&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;The current version is Yaffs2, which supports a wider range of NAND flash components including 2k/4k/8k or even 16k page devices and devices with multi-level cells (MLC), and produces equivalent or better performance. Yaffs2 include Yaffs1 compatibility code so Yaffs1 images still work and migration is quite simple. Yaffs1 or Yaffs2 mode of operation are simply selected by a run-time parameter.&lt;/p&gt;
&lt;p&gt;As well as providing a NAND file system, YDI also provides a RAM emulation layer to allow Yaffs to operate as a RAM file system too. While the RAM emulation is perhaps not as efficient as a dedicated RAM file system, this does allow one well proven file system to use both RAM and flash.&lt;/p&gt;
&lt;p&gt;Yaffs has been used for many products using various operating systems including Windows Embedded Compact (previously called Windows CE) and various RTOSs, including ThreadX, vXworks, pSOS to name just a few. Note that there is a native port of Yaffs to eCOS that does not use YDI. This is supported and distributed by eCocCentric.(&lt;a href=&quot;http://www.ecoscentric.com/&quot;&gt;http://www.ecoscentric.com/&lt;/a&gt;).&lt;/p&gt;
&lt;h2&gt;4 Why use Yaffs?&lt;/h2&gt;
&lt;p&gt;For an in depth understanding of the advantages of Yaffs, please read &lt;em&gt;&lt;a href=&quot;http://www.yaffs.net/documents/considerations-choosing-flash-file-system&quot;&gt;http://www.yaffs.net/documents/considerations-choosing-flash-file-system&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;For a brief overview: Yaffs is the first, and perhaps only, file system designed specifically for NAND flash. This means that Yaffs has been designed to work around the various limitations and quirks of NAND flash, as well as exploit the various features of NAND to achieve an effective file system.&lt;/p&gt;
&lt;p&gt;Some features to consider:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Yaffs has been well proven and has been used to ship in large volumes in several products using many different operating systems, compilers and processors.&lt;/li&gt;
&lt;li&gt;Yaffs is written in portable C and is endian neutral.&lt;/li&gt;
&lt;li&gt;Yaffs provides bad block handling and ECC algorithms to handle deficiencies in NAND flash.&lt;/li&gt;
&lt;li&gt;Yaffs is a log-structured file system which makes it very robust to corruptions caused by power failures etc.&lt;/li&gt;
&lt;li&gt;Yaffs has highly optimised and predictable garbage collection strategies. This makes it high performance and very deterministic when compared with similar file systems.&lt;/li&gt;
&lt;li&gt;Yaffs has a lower memory footprint than most other log-structured flash file systems.&lt;/li&gt;
&lt;li&gt;Yaffs provides a wide range of POSIX-style file system support including directories, symbolic and hard links etc. through standard file system interface calls.&lt;/li&gt;
&lt;li&gt;Yaffs is highly configurable to work with various flash geometries, various ECC options, caching options etc.&lt;/li&gt;
&lt;li&gt;Yaffs Direct Interface is simple to integrate in a system – only a few interface functions are required.&lt;/li&gt;
&lt;li&gt;Yaffs can be used with a wide range of memory technologies.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;5 What is Yaffs -for-VxWorks?&lt;/h2&gt;
&lt;p&gt;Many organizations have used Yaffs on VxWorks with just Yaffs Direct Interface (YDI). So what benefit does Yaffs-for-VxWorks offer?&lt;/p&gt;
&lt;p&gt;YDI provides a POSIX-like API, but with Yaffs specific names. For example: yaffs_open(), yaffs_read(), yaffs_close() etc.&lt;/p&gt;
&lt;p&gt;While YDI provides a solution for many systems, and is very well proven, it has one major drawback. It is not a native file system. That means:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Existing code that calls open(), read(), write() etc cannot be immediately used with YDI. The code needs to be rewritten to call the YDI functions: yaffs_open(), yaffs_read()... This porting is costly and error prone.&lt;/li&gt;
&lt;li&gt;Code written for YDI is then locked to Yaffs and makes portability/testability problems.&lt;/li&gt;
&lt;li&gt;Tools such as the VxWorks console shell cannot be used to access Yaffs files via YDI.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Yaffs-for-VxWorks fixes these limitations..&lt;/p&gt;
&lt;p&gt;Yaffs-for-VxWorks is a wrapper around YDI that plugs YDI in as a native file system (ie. Yaffs becomes a file system that is accessed no different from any of the other file systems on system. This makes it really easy to migrate existing VxWorks software, or develop new VxWorks software to get the benefits of Yaffs.&lt;/p&gt;
&lt;p&gt;Yaffs-for-VxWorks follows the VxWorks operating system model used by other VxWorks file systems, so it is easy for VxWorks developers to integrate Yaffs and integrate it with their normal workflow.&lt;/p&gt;
&lt;p&gt;As mentioned above, Yaffs-for-VxWorks is a wrapped version of YDI. That means all the testing and experience of using YDI since 2002 is incorporated into Yaffs-for-VxWorks.&lt;/p&gt;
&lt;p&gt;Yaffs is already supported in u-boot, so if you&#039;re using u-boot as a boot loader then there is already seamless support for Yaffs file system access between the boot loader and VxWorks.&lt;/p&gt;
&lt;p&gt;Some organizations have developed their own VxWorks wrappers for Yaffs, but using the Yaffs-for-VxWorks wrapper saves a lot of integration and testing effort.&lt;/p&gt;
&lt;p&gt;Once the Yaffs-for-VxWorks file system code is loaded into the kernel, flash devices are added using yaffs_devAdd(). They are then available in the VxWorks file system for access just like any other files in the system.&lt;/p&gt;
&lt;p&gt;&lt;img alt=&quot;Yaffs and VxWorks conceptual relationships&quot; src=&quot;/sites/yaffs.net/files/images/yaffs-vxworks.png&quot; /&gt;&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2&gt;6 Yaffs-for-VxWorks code&lt;/h2&gt;
&lt;p&gt;Yaffs-for-VxWorks is supplied as a VxWorks Downloadable Kernel Module (DKM) project with full source code. This can then be modifies into a BSP layer or library and compiled directly into the kernel.&lt;/p&gt;
&lt;p&gt;The code comprises Yaffs Direct Interface (YDI) plus two wrapper files:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;yaffs_drv.c: This file does all the iosLib interfacing (ie. plugs Yaffs in as a VxWorks file system and plugs in the flash devices as file system devices. This file provides one externally visible function call: yaffs_devAdd() which allows Yaffs devices (ie. Flash drivers) to be plugged in.&lt;/li&gt;
&lt;li&gt;yaffx_vx_glue.c: This file provides all the OS resources that Yaffs needs from VxWorks. For example, it initialises a semaphore and does any error code routing.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;In addition, if the Yaffs filesystem driver is build as a DKM, a file called yaffs_dkm.c provides the dummy DKM start() function.&lt;/p&gt;
&lt;p&gt;The code is provided as a DKM project. This includes the specification of the DEFINES needed to compile Yaffs under VxWorks. If the code is moved out of the DKM then it is important to make sure the correct DEFINES are set up.&lt;/p&gt;
&lt;h2&gt;7 Example Simulated Flash Driver&lt;/h2&gt;
&lt;p&gt;The Yaffs-for-VxWorks package provides an example Yaffs device that runs on a RAM simulator. This allows the file system to be tested in a simulation target without flash memory (eg the VxWorks simulator). This also provides an example for how to develop a flash driver and plug it in to Yaffs.&lt;/p&gt;
&lt;h2&gt;8 Example Real Time Process(RTP)&lt;/h2&gt;
&lt;p&gt;An example RTP is provided that performs some basic file system operations and demonstrates a working filesystem.&lt;/p&gt;
&lt;p&gt;This RTP uses standard file system calls (open(), read(), write()...) demonstrating that the Yaffs-for-VxWorks layer is operating as a native file system.&lt;/p&gt;
&lt;h2&gt;9 Integrating a Flash Device&lt;/h2&gt;
&lt;p&gt;Integrating a flash device is a relatively straight-forward process.&lt;/p&gt;
&lt;p&gt;The device is set up as a yaffs_device structure, which is then installed into Yaffs by calling the yaffs_devAdd() function.&lt;/p&gt;
&lt;p&gt;The NAND simulator can serve as an example for how to do this. The following snippet outlines the requirements. For a better description of the params and drv sub-structures refer to &lt;a href=&quot;http://www.yaffs.net/yaffs-tuning-and-configuration&quot;&gt;http://www.yaffs.net/yaffs-tuning-and-configuration&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;code&gt;struct yaffs_dev *yramsim_CreateRamSim(...)&lt;br /&gt;
{&lt;br /&gt;
...&lt;br /&gt;
&amp;nbsp; dev = malloc(sizeof(*dev));&lt;br /&gt;
...&lt;br /&gt;
&amp;nbsp; /* First set everything to NULL. */&lt;br /&gt;
&amp;nbsp; memset(dev, 0, sizeof(*dev));&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp; /*&amp;nbsp;&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* There are three sections to the yaffs_dev structure&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* that needs to be initialised:&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* * The params sub-structure which are all the control&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* parameters.&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* * The drv sub-structure which holds the driver functions.&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* * The context which holds a private pointer (used to hold a&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* driver context).&lt;br /&gt;
&amp;nbsp; &amp;nbsp;*/&lt;br /&gt;
&amp;nbsp; p = &amp;amp;dev-&amp;gt;param;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;name = strdup(name);&lt;br /&gt;
&amp;nbsp; p-&amp;gt;start_block = start_block;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;end_block = end_block;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;total_bytes_per_chunk = DATA_SIZE;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;spare_bytes_per_chunk= SPARE_SIZE;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;chunks_per_block = PAGES_PER_BLOCK;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;n_reserved_blocks = 2;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;use_nand_ecc = 1;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;inband_tags = 0;&lt;br /&gt;
&amp;nbsp; p-&amp;gt;is_yaffs2 = 1;&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp; d= &amp;amp;dev-&amp;gt;drv;&lt;br /&gt;
&amp;nbsp; d-&amp;gt;drv_initialise_fn = yramsim_initialise;&lt;br /&gt;
&amp;nbsp; d-&amp;gt;drv_deinitialise_fn = yramsim_deinitialise;&lt;br /&gt;
&amp;nbsp; d-&amp;gt;drv_read_chunk_fn = yramsim_rd_chunk;&lt;br /&gt;
&amp;nbsp; d-&amp;gt;drv_write_chunk_fn = yramsim_wr_chunk;&lt;br /&gt;
&amp;nbsp; d-&amp;gt;drv_erase_fn = yramsim_erase;&lt;br /&gt;
&amp;nbsp; d-&amp;gt;drv_check_bad_fn = yramsim_check_block_bad;&lt;br /&gt;
&amp;nbsp; d-&amp;gt;drv_mark_bad_fn = yramsim_mark_block_bad;&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp; dev-&amp;gt;driver_context= (void *)sim;&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp; return dev;&lt;br /&gt;
}&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
void start(void)&lt;br /&gt;
{&lt;br /&gt;
&amp;nbsp; int result;&lt;br /&gt;
&amp;nbsp; struct yaffs_dev *dev;&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp; printf(&quot;Yaffs RAMSIM started\n&quot;);&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp; /* Create and add a RAM simulator device.&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* To add a different sort of device, set up the device&lt;br /&gt;
&amp;nbsp; &amp;nbsp;* and call yaffs_devAdd.&lt;br /&gt;
&amp;nbsp; &amp;nbsp;*&amp;nbsp;&lt;br /&gt;
&amp;nbsp; &amp;nbsp;*/&lt;br /&gt;
&amp;nbsp; dev = yramsim_CreateRamSim(&quot;/yramsim&quot;, 0, 400, 0, 399);&lt;br /&gt;
&amp;nbsp; printf(&quot;device is %p\n&quot;, dev);&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
&amp;nbsp; if (dev) {&lt;br /&gt;
&amp;nbsp; result = yaffs_devAdd(dev);&lt;br /&gt;
&amp;nbsp; printf(&quot;yaffs_devAdd() returned %d\n&quot;, result);&lt;br /&gt;
&amp;nbsp; printf(&quot;yaffs RAM simulator now available in file system as %s&quot;,&lt;br /&gt;
&amp;nbsp; dev-&amp;gt;param.name);&lt;br /&gt;
&amp;nbsp;&lt;br /&gt;
}&lt;br /&gt;
}&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2&gt;10 Appendix: Running the examples on the VxWorks simulator&lt;/h2&gt;
&lt;p&gt;Once you have built the Yaffs_filesystem_driver and Yaffs_RAMSIM_device projects, you can start up Yaffs on the simulator as follows:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Start the simulator.&lt;/li&gt;
&lt;li&gt;Load the Yaffs_filesystem_driver DKM by right clicking on the Yaffs_filesystem_driver project, then selecting Run/Debug Kernel Task...&lt;/li&gt;
&lt;li&gt;Load the Yaffs_RAMSIM_device DKM by right clicking on the Yaffs_filesystem_driver project, then selecting Run/Debug Kernel Task...&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;At this stage the VxWorks console should look something like:&lt;/p&gt;
&lt;pre&gt;
 _________            _________

 \77777777\          /77777777/

  \77777777\        /77777777/

   \77777777\      /77777777/

    \77777777\    /77777777/

     \77777777\   \7777777/

      \77777777\   \77777/              VxWorks 7

       \77777777\   \777/

        \77777777\   \7/     Core Kernel version: 1.0.10.2

         \77777777\   -      Build date: Oct 13 2015 12:10:53

          \77777777\

           \7777777/         Copyright Wind River Systems, Inc.

            \77777/   -                 1984-2015

             \777/   /7\

              \7/   /777\

               -   -------


              Board: SIMLINUX board

     OS Memory Size: 511MB

   ED&amp;amp;R Policy Mode: Deployed

        Debug Agent: Started (always)

    Stop Mode Agent: Not started


Loading symbol table from charlesqcore:/home/charles/WindRiver/workspace/VIP_1/default/vxWorks.sym ...done

-&amp;gt; 

Yaffs file system DKM started

Yaffs flash devices can now be added by calling yaffs_devAdd()

Yaffs RAMSIM started

device is 0x8829e010

Adding Yaffs device 0x8829e010 (/yramsim)

yaffs_devAdd() returned 0

yaffs RAM simulator now available in file system as /yramsim&lt;/pre&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;At this stage you should be able to see the yaffs file system is running:&lt;/p&gt;
&lt;pre&gt;
-&amp;gt; ls &quot;/yramsim&quot;

/yramsim/lost+found 

value = 0 = 0x0

-&amp;gt; &lt;/pre&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;If you have built the yaffs_test project, then try running that. This should show something like:&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;pre&gt;
Start running Yaffs test

…

dump directory from pwd

./lost+found inode 2 length 2048 mode 41B6 directory


fs size: 52297728 (51072k), free 51642368 (50432k), n files 4

write_check_test()

opening a

Open of a returned 3

write_stuff_to_file returned 100000

…

Finished running Yaffs test&lt;/pre&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;Do a file listing &amp;nbsp;again will show the file system state after running the test:&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;pre&gt;
-&amp;gt; llr &quot;/yramsim&quot;


Listing Directory /yramsim:

drwxrwxrw-  1 0       0                 2048 Nov 25 14:07 level1/

-rw-rw-rw-  1 0       0                50505 Nov 25 14:07 seek-trunc 

-rw-rw-rw-  1 0       0               123000 Nov 25 14:07 s 

drw-rw-rw-  1 0       0                 2048 Nov 25 14:06 lost+found/


Listing Directory /yramsim/level1:

drwxrwxrw-  1 0       0                 2048 Nov 25 14:07 level2/


Listing Directory /yramsim/level1/level2:

drwxrwxrw-  1 0       0                 2048 Nov 25 14:07 level3/


Listing Directory /yramsim/level1/level2/level3:

drwxrwxrw-  1 0       0                 2048 Nov 25 14:07 level4/


Listing Directory /yramsim/level1/level2/level3/level4:


Listing Directory /yramsim/lost+found:

value = 0 = 0x0&lt;/pre&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;/div&gt;
      </description>
  <pubDate>Mon, 11 Jan 2016 15:28:55 +0000</pubDate>
    <dc:creator>Admin</dc:creator>
    <guid isPermaLink="false">479 at https://yaffs.net</guid>
    </item>
<item>
  <title>Considerations in Choosing a Flash File System</title>
  <link>https://yaffs.net/documents/considerations-choosing-flash-file-system</link>
  <description>&lt;span&gt;Considerations in Choosing a Flash File System&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/laurie&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Laurie&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;28 May, 2014 - 1:53pm&lt;/span&gt;

      &lt;div class=&quot;field field--name-upload field--type-file field--label-hidden field--items&quot;&gt;
              &lt;div class=&quot;field--item&quot;&gt;&lt;span class=&quot;file file--mime-application-pdf file--application-pdf icon-before&quot;&gt;&lt;span class=&quot;file-icon&quot;&gt;&lt;span class=&quot;icon glyphicon glyphicon-file text-primary&quot; aria-hidden=&quot;true&quot;&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&quot;file-link&quot;&gt;&lt;a href=&quot;https://yaffs.net/sites/default/files/downloads/ConsiderationsInChoosingAFlashFileSystem_0.pdf&quot; type=&quot;application/pdf; length=131376&quot; title=&quot;Open file in new window&quot; target=&quot;_blank&quot; data-toggle=&quot;tooltip&quot; data-placement=&quot;bottom&quot;&gt;ConsiderationsInChoosingAFlashFileSystem.pdf&lt;/a&gt;&lt;/span&gt;&lt;span class=&quot;file-size&quot;&gt;128.3 KB&lt;/span&gt;&lt;/span&gt;&lt;/div&gt;
          &lt;/div&gt;
  
            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;
&lt;p&gt;We have been developing flash file system for embedded systems since 1995. During that time, we have gained a wealth of knowledge and experience.&lt;/p&gt;
&lt;p&gt;This document outlines some of the major issues that must be considered when selecting a Flash File system for embedded use. It also explains how using the Yaffs File System increases reliability, reduces risk and saves money.&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;Introduction&lt;/h1&gt;
&lt;p&gt;As embedded system complexity increases and flash storage prices decrease, we see more use of embedded file systems to store data, and so data corruption and loss has become an important cause of system failure.&lt;/p&gt;
&lt;p&gt;When Aleph One began the development of Yaffs in late 2001, we built on experience in flash file system design since 1995. This experience helped to identify the key factors in making Yaffs a fast and robust flash file system now being widely used around the world.&lt;/p&gt;
&lt;p&gt;Although it was originally developed for Linux, Yaffs was designed to be highly portable. This has allowed Yaffs to be ported to many different OSs (including Linux, BSD, Windows CE) and numerous RTOSs (including VxWorks, eCos and pSOS).&lt;/p&gt;
&lt;p&gt;Yaffs is written in fully portable C code and has been used on many different CPU architectures – both little- and big-endian. These include ARM, x86 and PowerPC, soft cores such as NIOS and Microblaze and even various DSP architectures.&lt;/p&gt;
&lt;p&gt;We believe that the Yaffs code base has been used on more OS types and more CPU types than any other file system code base.&lt;/p&gt;
&lt;p&gt;Since its introduction, Yaffs has been used in hundreds of different products and hundreds of millions of different devices in widely diverse application areas from mining to aerospace and everything in between.&lt;/p&gt;
&lt;p&gt;Specific examples include:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;communications (two-way radios and infrastructure, mobile phones, cell towers, modems, routers...)&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;retail (point of sale, inventory control...)&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;entertaiment (video cameras, TV sets, DVD players, set-top boxes...)&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;sewing machines and office copiers&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;industrial equipment (PLCs, machinery control...)&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;construction/surveying equipment (theodolites, machinery control...)&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;avionics and satellite equipment&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;transport (bus, train and traffic-signal management/information systems...)&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;and many more.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;You may be using Yaffs every day without even realising it.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;We have a gratifying number of repeat customers for licences.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;h1 class=&quot;western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/h1&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;Do Embedded Systems have different file system needs?&lt;/h1&gt;
&lt;p&gt;To answer this question, we really have to start by asking a slightly different question:&lt;/p&gt;
&lt;p&gt;&lt;i&gt;How are embedded systems different than regular computers?&lt;/i&gt;&lt;/p&gt;
&lt;p style=&quot;font-style: normal&quot;&gt;When a customer buys a regular computer system, they go shopping for a computer. They talk to the salesperson about Gigabytes, Megahertz and operating systems. They treat it as a computer and expect it to behave like a computer (including shutting it down properly and occasionally having file system problems or needing upgrades).&lt;/p&gt;
&lt;p style=&quot;font-style: normal&quot;&gt;When they buy a fancy sewing machine, it probably has an embedded file system controlling it. The customer went shopping for a sewing machine and bought a computer that they don&#039;t even know about. They don&#039;t treat it like a computer, but like a sewing machine; they certainly do not expect it to have file system problems.&lt;/p&gt;
&lt;h4 class=&quot;western&quot;&gt;How people treat computers differently from embedded systems&lt;/h4&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;page-break-inside: avoid; width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;85*&quot; /&gt; &lt;col width=&quot;85*&quot; /&gt; &lt;col width=&quot;85*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;Issue&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;Computer&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;Embedded system&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Shut down&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;User expects to do a clean shut down.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;User just unplugs device.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Reinstalling software&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Users expect to have to deal with corruption and reinstall software occasionally.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Users do not expect to deal with upgrades or data loss or corruption.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%; height: 11px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Software Upgrade Failure&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Annoying&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Can be devastating&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Attitude to data loss&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Annoying, but expected&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;System has failed.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Cost of failure&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Relatively minor&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Can shut down factory or even cause injury/death.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Delayed boot due to file system recovery&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Annoying, but expected.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 33%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;This is as bad as a failure.&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p style=&quot;font-style: normal&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;So people have different attitudes to computers and embedded systems. As a result, embedded systems need to be designed differently from computers. That is particularly important with reliability issues.&lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0.01cm&quot;&gt;&lt;i&gt;&lt;b&gt;Data corruption is a leading cause of embedded system failure, &lt;/b&gt;&lt;/i&gt; &lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0.01cm&quot;&gt;&lt;i&gt;&lt;b&gt;product returns and warranty costs.&lt;/b&gt;&lt;/i&gt; &lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0.01cm&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;The differences outlined above show some of the reasons why embedded systems must perform differently to regular computers, particularly in the way data storage is handled. These examples allow us to identify some very important product-level criteria for embedded file systems:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;High resilience against data corruption, particularly in the event of power loss.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Prompt file system recovery after power loss - no excessive time penalty&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Simple data integrity model to ensure data is not compromised.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Of course we also want the embedded file system to have some other very useful features:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;High read/write performance with low latency.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Familiar programming models to facilitate development.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Proven track record to reduce risk.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Full source code access to aid development.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Portability to provide a future-proof solution for new products.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;Selecting an appropriate file system is crucial to product success.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;Why does power failure corrupt data?&lt;/h1&gt;
&lt;p&gt;Most power fail data loss in a File System is caused through two mechanisms:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Corruption of allocation tables &lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Loss of cached data that was not yet written to the flash.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 class=&quot;western&quot;&gt;Corruption of allocation tables and similar structures.&lt;/h2&gt;
&lt;p&gt;Most file systems have allocation tables, bitmaps or similar structures which hold pointers showing which parts of the file storage medium are being used and which parts of which file are stored there. These tables are critical to looking up files and data in the file system. If they are corrupted, then files and data become corrupted. In the most dramatic cases, table corruption can destroy the whole system. &lt;/p&gt;
&lt;p&gt;Some file systems make these tables more robust by keeping two copies, or by using journaling (which keeps a short log of changes, allowing the tables to be fixed up if the table changing gets interrupted) but this causes extra writes to the media, making the file system slower.&lt;/p&gt;
&lt;p&gt;These tables are typically updated many times during writing any file, so there are multiple opportunities for the tables to be corrupted or left in an inconsistent state due to a power loss.&lt;/p&gt;
&lt;p&gt;If power is interrupted at a critical point, then some restoration (such as Microsoft chkdsk or booting in &lt;span style=&quot;font-style: normal&quot;&gt;safe mode&lt;/span&gt;) is often required to try to restore the tables. This may be automatic, but then system start-up is delayed.&lt;/p&gt;
&lt;p&gt;Yaffs is very different; it is a log structured file system which writes tagged data to the flash, and does not store allocation tables or such.&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;If it isn&#039;t even stored, it can&#039;t be corrupted!&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;This has three dramatic effects:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Yaffs has no tables, so is immune to these failure modes.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;There are no extra tables to be written, so Yaffs does not have to resort to caching to achieve good performance.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Fewer flash writes means less flash wear, improving product life and reducing power consumption.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;When a Yaffs file system is booted, the normal boot up sequence takes care of building up system state. There is thus no need for any special restoration code to be run. A boot up after a power failure is not a special recovery condition, it is just a normal boot up.&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;Yaffs does not have, or need, special recovery handling.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;h2 class=&quot;western&quot; style=&quot;page-break-after: avoid&quot;&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;i&gt;&lt;b&gt;Trade-off in cached data&lt;/b&gt;&lt;/i&gt;&lt;/span&gt;&lt;/h2&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;File systems tend to be inefficient in the way they write data. Writing just one file requires many changes to the allocation tables; writing many files requires far more changes, often to those same tables. By delaying those writes and holding data in RAM briefly the file system can do fewer writes to achieve the same set of changes. This can improve write speed, at a price.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Data which has not been written but just cached in RAM is vulnerable while it is there; it can all be lost if power fails, even including some that the FS had apparently written already.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Most file systems support functions to reduce this inefficiency and force the cache to be written out, but this may take many seconds, leaving a significant period of vulnerability, and delaying system operations. Excessive use of these functions to improve reliability will typically impair write performance.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;A particularly serious example of critical data loss can occur if power or communication fails during a firmware upgrade. Such a failure cripples the product, which must be returned for servicing. Yaffs has caching policies and data integrity models which make it easier to avoid this kind of fatal failure, and which have been tested very extensively. &lt;/span&gt;&lt;/span&gt; &lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;Since Yaffs is inherently faster and simpler, it does not need deep caching. The Yaffs cache is small and used only for data alignment purposes and improving the throughput of very small reads and writes. Yaffs files are always flushed from the cache when they are closed. Yaffs also provides its own cache-flushing functions, but these are very fast because the cache is small.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;&lt;i&gt;&lt;b&gt;By the time Yaffs closes a file, all the data is guaranteed to be safe on the flash.&lt;/b&gt;&lt;/i&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;This simple caching policy makes it very easy for programmers to write software that is robust against power loss and avoids obscure failure modes. The simplicity confers more reliable operation, faster product development and huge savings in development and maintenance costs.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Sans, sans-serif;&quot;&gt;&lt;span style=&quot;font-size: 11pt; font-size: small; font-size: small;&quot;&gt;&lt;i&gt;&lt;b&gt;Reliable file systems pay for themselves many times over.&lt;/b&gt;&lt;/i&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;Product risk reduction&lt;/h1&gt;
&lt;p&gt;At first glance, a file system seems like it should be a simple body of code: just a few functions that read, write data and look things up by name. However, the reality is much more complex than that.&lt;/p&gt;
&lt;p&gt;One of the most challenging aspects of file systems is that errors are stored and incremental. Unlike most software errors which can be cleared by a reset, storage errors are persistent.&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;A reboot will typically not fix file-system errors.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;Customers might tolerate a product that needs to be reset once in a while, but file system failures are often fatal. As a result, file system issues can be very damaging to long-term product reliability.&lt;/p&gt;
&lt;p&gt;This is further complicated by flash memory. NAND flash is the only type of semiconductor hardware which leaves the factory with known variable errors, expecting the file system software to handle the problems.&lt;/p&gt;
&lt;p&gt;Flash, NAND in particular, has its own failure modes and these are best handled by a file system specifically designed for NAND.&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;Yaffs was specifically designed to use with NAND and NOR flash chips.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;Flash memory chip errors may only show up after the product has been used a while, or in a fraction of the flash parts. Typical testing during development (e.g. bench testing) will often fail to expose all types of flash chip error, and others will only be exposed during pilot- or early-production. These put release dates at risk, which can cause huge revenue losses.&lt;/p&gt;
&lt;p&gt;We have a few clients who only determined that they had file system issues when they did a pilot run. That prompted them to try Yaffs and get their products shipping. While we are glad they ended up with a good product, unfortunately they lost revenue and customer goodwill.&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;Finding problems late in development creates business risk.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;It is thus not surprising that much of our business is repeat business. &lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;Yaffs testing&lt;/h1&gt;
&lt;p&gt;Testing on its own does not create good software but it does help to verify that the software is working correctly.&lt;/p&gt;
&lt;p&gt;Yaffs has many automated tests that are run on a regular basis. Automated tests allow the testing to be run without human intervention, thus allowing more testing to be done.&lt;/p&gt;
&lt;p&gt;The tests are too numerous to discuss completely (see the Further Information below). W&lt;span style=&quot;font-weight: normal&quot;&gt;e&lt;/span&gt; highlight one: the power-fail stress test.&lt;/p&gt;
&lt;p&gt;The power-fail stress test is a test harness that uses software simulations of flash devices and some software and scripts to simulate the effects of removing power from a Yaffs-based system &lt;span style=&quot;font-weight: normal&quot;&gt;while it is writing&lt;/span&gt; to flash. This test is normally run for 100,0000 to 1 million power-fail simulation cycles, taking many days.&lt;/p&gt;
&lt;p&gt;This particular test suite was originally developed in 2008 during the development of some new features. The tests are very rigorous. In the beginning, this test suite would find a problem after less than 100 power fail iterations. As we identified and fixed the bugs, this number crept up and we now run millions of cycles without seeing a single problem.&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;Yaffs survives millions of power failures in simulation test benches.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;In addition, many of our clients have also run hardware power failure tests, using a relay and a micro-controller to kill power to the device under test. They have been very satisfied with the results.&lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0cm; orphans: 0; widows: 0; page-break-before: auto&quot;&gt;&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-size: 16pt; font-size: large; font-size: large;&quot;&gt;&lt;b&gt;Licensing&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;Yaffs is available under GNU Public License V2, GPL2, from our git repository at &lt;a href=&quot;http://www.yaffs.net/&quot;&gt;www.yaffs.net&lt;/a&gt;. You may use that code for testing free of charge and for as long as you want.&lt;/p&gt;
&lt;p style=&quot;font-weight: normal&quot;&gt;&lt;i&gt;You will be using it under the conditions of GPL2 with the obligation to release your associated source code when you start to sell or distribute a product.&lt;/i&gt;&lt;/p&gt;
&lt;p style=&quot;font-weight: normal&quot;&gt;&lt;i&gt;We can then sell you a Licence to use Yaffs which removes that obligation and protects your intellectual property.&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;With Yaffs you can try before you buy!&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;h1 class=&quot;western&quot;&gt;Conclusions&lt;/h1&gt;
&lt;p&gt;Selecting a robust flash file system is key to :&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;building a successful product.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;reducing risk, warranty costs and liability.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;reducing development costs.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;i&gt;&lt;b&gt;Yaffs has proven itself and can pay for itself many times over.&lt;/b&gt;&lt;/i&gt;&lt;/p&gt;
&lt;h1 class=&quot;western&quot;&gt;Further information&lt;/h1&gt;
&lt;p&gt;This document is intentionally brief. There are many documents at &lt;a href=&quot;http://www.yaffs.net/&quot;&gt;http://www.yaffs.net&lt;/a&gt; for those that want more information, including:&lt;/p&gt;
&lt;p&gt;&lt;b&gt;How Yaffs Works:&lt;/b&gt; detailed description of internal design.&lt;/p&gt;
&lt;p&gt;&lt;b&gt;Yaffs Robustness and Testing:&lt;/b&gt; how we know Yaffs handles various flash failure scenarios.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;For further information please contact &lt;a href=&quot;denied:mailto:info@yaffs.net&quot;&gt;info@yaffs.net&lt;/a&gt; or access &lt;a href=&quot;http://www.yaffs.net/&quot;&gt;http://www.yaffs.net&lt;/a&gt;&lt;/p&gt;
&lt;/div&gt;
      </description>
  <pubDate>Wed, 28 May 2014 12:53:29 +0000</pubDate>
    <dc:creator>Laurie</dc:creator>
    <guid isPermaLink="false">466 at https://yaffs.net</guid>
    </item>
<item>
  <title>Yaffs NAND flash failure mitigation</title>
  <link>https://yaffs.net/documents/yaffs-nand-flash-failure-mitigation</link>
  <description>&lt;span&gt;Yaffs NAND flash failure mitigation&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/admin&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Admin&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;23 July, 2012 - 1:29am&lt;/span&gt;

      &lt;div class=&quot;field field--name-upload field--type-file field--label-hidden field--items&quot;&gt;
              &lt;div class=&quot;field--item&quot;&gt;&lt;span class=&quot;file file--mime-application-pdf file--application-pdf icon-before&quot;&gt;&lt;span class=&quot;file-icon&quot;&gt;&lt;span class=&quot;icon glyphicon glyphicon-file text-primary&quot; aria-hidden=&quot;true&quot;&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&quot;file-link&quot;&gt;&lt;a href=&quot;https://yaffs.net/sites/default/files/downloads/YaffsNandFailureMitigation.pdf&quot; type=&quot;application/pdf; length=235109&quot; title=&quot;Open file in new window&quot; target=&quot;_blank&quot; data-toggle=&quot;tooltip&quot; data-placement=&quot;bottom&quot;&gt;YaffsNandFailureMitigation.pdf&lt;/a&gt;&lt;/span&gt;&lt;span class=&quot;file-size&quot;&gt;229.6 KB&lt;/span&gt;&lt;/span&gt;&lt;/div&gt;
          &lt;/div&gt;
  
            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;h2&gt;1 Purpose&lt;/h2&gt;
&lt;p&gt;The purpose of this document is to give an understanding of NAND failure modes and the measures that Yaffs takes to mitigate against these.&lt;/p&gt;
&lt;p&gt;This document is intended to be easy reading, but some very light-weight physics is required to understand the way NAND works.&lt;/p&gt;
&lt;h2&gt;2 The NAND Cell&lt;/h2&gt;
&lt;p&gt;This section explains the internal construction of a NAND device which helps to explain the way that it fails. Each NAND cell consists of a floating gate field effect transistor, described below.&lt;/p&gt;
&lt;h3&gt;2.1 Floating Gate Field Effect Transistor&lt;/h3&gt;
&lt;p&gt;A FET is the fundamental switching element used in almost all digital electronics. A FET is a a semiconductor element that conducts when a charge is applied to the gate.&lt;/p&gt;
&lt;p&gt;&lt;img alt=&quot;&quot; src=&quot;/sites/yaffs.net/files/images/fets.gif&quot; /&gt;&lt;/p&gt;
&lt;p&gt;A FET is a type of semiconductor device with a semiconducting region between the the source and drain connections, an insulating oxide and a gate region. The oxide prevents current from flowing from the gate to the oxide, but applying a voltage to the gate injects charge into the gate, creating an electric field which influences the conductive properties of the semiconductor region.&lt;/p&gt;
&lt;p&gt;In a regular FET, a conductive channel is formed between the source and drain when a suitable control voltage is applied to the gate. The current passed by the channel is dependent on the voltage (ie. the strength of the gate field). For now we will ignore analogue levels and just consider binary levels where the gate is either conducting or not. This effectively makes a switch that is controlled by the control gate.&lt;/p&gt;
&lt;p&gt;The floating gate FET is just like a regular FET except that it has an extra floating gate. This floating gate is able to trap charge between the two insulating layers. The trapped charge modifies the local electric field and thus modifies the effect of the control gate. If the floating gate has extra electrons (negative charge) then the control gate must be raised to a higher voltage to make the FET conduct.&lt;/p&gt;
&lt;p&gt;So a regular FET is conductive (on) when the control gate is high and is non-conductive (off) when the control gate is low. A floating gate FET, however, is only non-conductive (off) when the floating gate is charged and the gate is low. This gives us an output that is dependent on the floating gate and a way to read it (the gate).&lt;/p&gt;
&lt;table&gt;
&lt;colgroup&gt;
 &lt;col /&gt; &lt;col /&gt; &lt;col /&gt;
&lt;/colgroup&gt;
&lt;tbody&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Floating gate charge&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Control gate&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Source/drain channel&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Neutral(unprogrammed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;High&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;On (1)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Neutral(unprogrammed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Low&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;On (1)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Charged(programmed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;High&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;On (1)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Charged(programmed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Low&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Off (0)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&amp;nbsp;&lt;/p&gt;
&lt;p&gt;The tunneling oxide is insulating at low voltages but allows quantum tunneling (Fowler-Nordheim tunneling) at higher voltages. This FN-tunneling provides a mechanism to inject or remove charge from the floating gate by applying high voltages to the control gate or the body.&lt;/p&gt;
&lt;p&gt;&lt;img alt=&quot;&quot; src=&quot;/sites/yaffs.net/files/images/fn-tunnelling.gif&quot; /&gt;&lt;/p&gt;
&lt;p&gt;By applying a high positive voltage to the control gate, electrons are drawn into the floating gate, resulting in a programmed gate. Erasing is accomplished by the reverse operation which draws electrons out of the gate.&lt;/p&gt;
&lt;p&gt;So a floating gate FET is effectively a readable, programmable switch. In other words: memory!&lt;/p&gt;
&lt;h3&gt;2.2 NAND array layout&lt;/h3&gt;
&lt;p&gt;NAND flash gets its name from the way that the cells are arranged. NAND cells are arranged in chains called &lt;em&gt;&lt;strong&gt;strings&lt;/strong&gt;&lt;/em&gt;, typically 1 string per bit-position in the page n(for SLC). The length of the chain is the same as the number of pages per block. This arrangement uses far less silicon area than the NOR flash arrangement which reduces NAND cost and increases density. It does however also introduce some operational and reliability problems.&lt;/p&gt;
&lt;p&gt;&lt;img alt=&quot;&quot; src=&quot;/sites/yaffs.net/files/images/nand-page-select.gif&quot; /&gt;&lt;/p&gt;
&lt;p&gt;NAND is read by biasing the unselected pages with a high bias voltage and the selected pages with the low bias voltage. This means that the unselected cells are always on and the selected cells will be on or off according to the state of the floating gate.&lt;/p&gt;
&lt;p&gt;This means we have a matrix where:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;All unselected cells are on.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Selected unprogrammed cells are on&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Selected programmed cells are off.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Since only one cell in a string is selected at a time, the whole string is on if the selected cell is unprogrammed and is off if the selected cell is programmed. Thus, even though the cells in a string are all in series we can still access them individually.&lt;/p&gt;
&lt;p&gt;Well, that&#039;s how it would work in a perfect world anyway!&lt;/p&gt;
&lt;p&gt;The string and block arrangement means that it takes quite a while ( typically a few µsec) for the voltage of the string to stabilize after the selection has been made. This stabilization time is the cause of the “access time” delay when accessing NAND flash.&lt;/p&gt;
&lt;h3&gt;3 Fault Modes&lt;/h3&gt;
&lt;p&gt;Sit back for a moment and consider everything that must come together for the NAND flash to work and all the ways things can go wrong:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Of course there can be fabrication faults where defects cause short circuits and open circuits within the chip. These types of fault apply to all chips type, not just flash.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Each cell has two oxide layers trapping the floating gate charge, one of which is semi-permeable to support tunneling. If either of these layers is too thick, the gate will be unresponsive. If they are too thin then the gate will tunnel too easily or will leak. If there are impurities in the oxide then the layers may become resistive and “leak”, thus causing the charge to change and possibly causing the state to change.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;The floating gate state can change by either gaining or losing charge. If charge is lost, then a programmed cell may become unprogrammed (a 0 changes to a 1). If charge is gained, then an unprogrammed cell can become programmed.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;In very extreme cases, a programmed cell can gain further negative charge and become over-programmed. This means that even if the high read bias voltage is applied to the control gate the FET does not become conductive. In this state, a cell will read as programmed (0) even if it is not selected. This means that the whole string will always read zero irrespective of which page is selected. This fault mode will persist until the cell is erased.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;These devices are made very cheaply. Flash parts with tens of billions of NAND cells cost only a few dollars. There is little money to spend on individual part testing.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Extending the previous state/selection table with the over-programmed fault state, we now have:&lt;/p&gt;
&lt;table&gt;
&lt;colgroup&gt;
 &lt;col /&gt; &lt;col /&gt; &lt;col /&gt;
&lt;/colgroup&gt;
&lt;tbody&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Floating gate charge&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Control gate&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Source/drain channel&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Neutral(unprogrammed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;High&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;On (1)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Neutral(unprogrammed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Low&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;On (1)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Charged(programmed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;High&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;On (1)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Charged(programmed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Low&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Off(0)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Over-charged(over-programmed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;High&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Off(0)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Over-charged(over-programmed)&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Low&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Off(0)&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;h2&gt;4 Fault Mechanisms&lt;/h2&gt;
&lt;p&gt;This section explains some of the common NAND flash failure modes.&lt;/p&gt;
&lt;h3&gt;4.1 General chip fault&lt;/h3&gt;
&lt;p&gt;A NAND is a chip built with normal fabrication techniques and is thus prone to fail just like any other chip. Some of these faults can be isolated by marking faulty blocks. In some cases (eg. Damaged inter-block logic) the whole chip is discarded.&lt;/p&gt;
&lt;p&gt;Yaffs does not use the bad blocks, so they have no negative impact on the performance of the file system 9apart from a small reduction in the amount of storage available).&lt;/p&gt;
&lt;h3&gt;4.2 Oxide degradation&lt;/h3&gt;
&lt;p&gt;Every programming/erasure cycle causes some degradation of the oxide layers. Over many cycles this has a tendency to degrade the properties of the oxide layer. Excessive degradation can cause the cell to fail to erase or program, but more commonly just makes the other fault modes more prevalent.&lt;/p&gt;
&lt;p&gt;The primary mechanism of oxide degradation is that charge becomes permanently trapped within the oxide layer in a way that it is not cleared by programming and erasure. The resulting field disrupts both the FET&#039;s conductive channel and the effectiveness of the F-N tunneling.&lt;/p&gt;
&lt;p&gt;As a result of this field disruption, two things happen:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;The FN tunneling is disrupted which means that the programming and erasure take longer to complete. Eventually programming and erasure might fail (see Program/erase failure below).&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;The programming and erasure is far more marginal meaning that less leakage is required to corrupt a bit value (see Charge leakage below).&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;This degradation is permanent and incremental and is not cleared by erasure. This degradation is the cause of the endurance term in the NAND specification. Typical NAND flash endurance is 10,000 (MLC) to 100,000(SLC) program/erasure cycles.&lt;/p&gt;
&lt;p&gt;Endurance issues are largely minimized by wear leveling and write-path caching.&lt;/p&gt;
&lt;p&gt;Blocks that become too unreliable are retired from use.&lt;/p&gt;
&lt;h3&gt;4.3 Program/erase failure&lt;/h3&gt;
&lt;p&gt;Programming and erase operations are controlled by a built-in state machine that applies the programming/erasure voltages for a while then check whether the operation has succeeded. This is typically performed by an iterative algorithm that will time out if too many cycles are required.&lt;/p&gt;
&lt;p&gt;A failure is signaled in the chip status register when the built-in programming/erasure mechanisms fail to accomplish the programming or erasure within the maximum program/erasure time.&lt;/p&gt;
&lt;p&gt;It is important to realize that a programming failure is only checked on bits being set to a zero. If one bits are inadvertently set to zero then these are not raised as programming errors but are considered to be program disturb errors.&lt;/p&gt;
&lt;p&gt;Program/erase errors are generally the result of excessive oxide degradation.&lt;/p&gt;
&lt;p&gt;Yaffs handles programming/erasure errors as unrecoverable “hard errors”. If these are encountered then useful data is copied off the block and the whole block is permanently retired by marking the block as a bad block.&lt;/p&gt;
&lt;p&gt;These are the only failures that the NAND devices will actually identify. All other failures need to be detected in software.&lt;/p&gt;
&lt;h3&gt;4.4 Charge leakage&lt;/h3&gt;
&lt;p&gt;The oxide isolating the floating gate is not a perfect insulator and charge can escape very slowly, particularly at temperature extremes and when the oxide had been degraded by extensive use. High radiation environments can also make this worse.&lt;/p&gt;
&lt;p&gt;An effective way to handle charge leakage is to use ECC to detect and correct errors. Blocks with errors are rewritten on a fresh block allowing the data to be recreated before unrecoverable errors occur.&lt;/p&gt;
&lt;h3&gt;4.5 Program disturb&lt;/h3&gt;
&lt;p&gt;Program disturb happens when a bit is unintentionally programmed (1 to 0) during a programming operation. The affected bit can be in the same page or elsewhere in the block.&lt;/p&gt;
&lt;p&gt;Program disturb is caused by bias conditions in the flash block during programming. Even though full programming voltage is only applied to the cells being programmed, the other cells are also subject to lesser voltages and minor tunneling can occur. This effect is far less than regular programming but is more than read disturb. However, since a page is only programmed once before the block is erased, there is no multiplier effect as there is in read disturb.&lt;/p&gt;
&lt;p&gt;This condition is made worse by random programming in the block and by applying multiple partial writes to the pages.&lt;/p&gt;
&lt;p&gt;Yaffs1 only writes pages in a block in sequential order and writes pages only once, except for writing deletion markers.&lt;/p&gt;
&lt;p&gt;Yaffs2 does not write deletion markers and thus only programs pages sequentially and only once.&lt;/p&gt;
&lt;p&gt;Thus, Yaffs2 is far less likely to cause write disturb. Yaffs1 should only be used with devices that are tolerant of partial page programming.&lt;/p&gt;
&lt;p&gt;Program disturb within the same page can be corrected by verifying the page after programming.&lt;/p&gt;
&lt;p&gt;ECC provides a mechanism to correct infrequent program disturb errors.&lt;/p&gt;
&lt;h3&gt;4.6 Read disturb&lt;/h3&gt;
&lt;p&gt;Whenever a page is read, the other pages in the block are biased at a read-inhibit voltage to turn them on. While this voltage is not as high as the programming voltage, some very slight F-N tunneling can occur. With sufficient leakage the cell state may change, or the cell may become over-programmed. This effect is known as read disturb.&lt;/p&gt;
&lt;p&gt;Read disturb only impacts the pages in the block that are &lt;em&gt;&lt;strong&gt;not&lt;/strong&gt;&lt;/em&gt; &lt;strong&gt;&lt;/strong&gt;being read. This makes it difficult to detect in some systems. For example, consider a block where only the first page is read repeatedly. Other pages in the block may be incurring read disturb but these are happening without the effect being noticed by software. By the time the pages are eventually read, the read disturb may have caused more bit errors than the ECC is able to fix.&lt;/p&gt;
&lt;p&gt;Thankfully the problem is seldom that bad. Read disturb is very gradual. Under worst case conditions read disturb effects are expected to happen only after approximately 1 million page reads on the block for SLC flash or 100,000 page reads on the block for most MLC flash (or in other words, 10 times the endurance number).&lt;/p&gt;
&lt;p&gt;Be warned though that as process sizes shrink, read disturb is getting more problematic. Some flash parts are prone to read disturb after 20,000 page reads.&lt;/p&gt;
&lt;p&gt;The read disturb effect for a single read is far less than the write disturb effect for a single write. However, each page is only written once per block erase cycle but may be read many times. Therefore the cumulated effect of many read disturbs can cause problems.&lt;/p&gt;
&lt;p&gt;Read disturb effects are cleared by erasing the block.&lt;/p&gt;
&lt;p&gt;Various mechanisms are being implemented to correct read disturb in Yaffs, though these have not yet been implemented.&lt;/p&gt;
&lt;p&gt;The first mechanism is to count the number of page reads on each block. When a certain threshold is reached (say 50,000 reads for an MLC part), the block is rewritten and the count is zeroed.&lt;/p&gt;
&lt;p&gt;The second mechanism is to periodically read pages in the block. eg. Every 256 times a block has a page read we read an additional page to check for read disturb. If read disturb has happened then copy onto a fresh page.&lt;/p&gt;
&lt;p&gt;In addition, ECC does provide some benefit, but is insufficient on its own.&lt;/p&gt;
&lt;h2&gt;5 Decoding NAND reliability statistics&lt;/h2&gt;
&lt;p&gt;Many variables contribute to NAND reliability. These variables are inter-related in complex ways which mean that is is very difficult to try to isolate the variables from each other to fully characterize them. The major variables are:&lt;/p&gt;
&lt;table&gt;
&lt;colgroup&gt;
 &lt;col /&gt; &lt;col /&gt;
&lt;/colgroup&gt;
&lt;tbody&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Temperature&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Temperature impacts the performance of the materials and thus impacts the movement of charge within the NAND cells.&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Storage time&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;This is related to the cell leakage. The leakage integrates over time so the longer the cells are stored, the more it changes.&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Manufacturing variance&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Operating voltage&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Erasure/programming cycles&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;Read cycles&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;h2&gt;6 MLC vs SLC&lt;/h2&gt;
&lt;p&gt;Both multi-level cell (MLC) and single-level cell (SLC) NAND cells work by trapping charge in the floating gate. By trapping different amounts of charge in the gate it is possible to modify the conductance of the string. MLC store two bits in once cell by using three threshold voltages to distinguish different cell charge levels&lt;a href=&quot;#sdfootnote1sym&quot;&gt;1&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&lt;img alt=&quot;&quot; src=&quot;/sites/yaffs.net/files/images/nand-mlc-vs-slc-cell-voltages.gif&quot; /&gt;&lt;/p&gt;
&lt;p&gt;In the case of SLC, the cells are erased by the erasure state machine until the cell voltage is below V erase. Programming is accomplished by programming until the voltage exceeds Vprog. On reading, the voltage is compared with Vread.&lt;/p&gt;
&lt;p&gt;MLC programming is accomplished in the same way, except that there are multiple Vprogs and Vreads. This means that there is far less margin for error and cell disturbance is far more likely to cause state changes.&lt;/p&gt;
&lt;p&gt;For this reason, MLC is less reliable, has lower endurance numbers and lower read-disturb numbers. MLC thus requires far better ECC strategies to ensure reliable storage.&lt;/p&gt;
&lt;p&gt;But MLC is cheaper!&lt;/p&gt;
&lt;h2&gt;7 Summary&lt;/h2&gt;
&lt;p&gt;In summary, NAND flash has many failure modes but these can be corrected in software to provide a reliable storage solution. Any flash storage mechanisms that do not provide sufficient coverage of different fault modes should be considered suspect.&lt;/p&gt;
&lt;table&gt;
&lt;colgroup&gt;
 &lt;col /&gt; &lt;col /&gt; &lt;col /&gt; &lt;col /&gt; &lt;col /&gt; &lt;col /&gt; &lt;col /&gt;
&lt;/colgroup&gt;
&lt;tbody&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Chip Fault&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Degradation&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;P/E failure&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Leakage&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Write Disturb&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Read Disturb&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;NAND self check&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Block retirement&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Wear levelling&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Write Verification&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Read counting/ re-write&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Future&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Infrequent read checking&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Future&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Future&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Future&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;ECC&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
 &lt;tr&gt;
  &lt;td&gt;
  &lt;p&gt;&lt;strong&gt;Occasional rewrite of oldest data&lt;/strong&gt;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;&amp;nbsp;&lt;/p&gt;
   &lt;/td&gt;
  &lt;td&gt;
  &lt;p&gt;Yes&lt;/p&gt;
   &lt;/td&gt;
 &lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Thus all fault mechanisms are covered by at least two corrective mechanisms (read disturb correcting features are planned).&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;#sdfootnote1anc&quot;&gt;1&lt;/a&gt;Some MLC parts store more than 2 bits per cell, Storing n bits requires 2n levels.&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&amp;nbsp;&lt;/p&gt;
&lt;/div&gt;
      </description>
  <pubDate>Mon, 23 Jul 2012 00:29:01 +0000</pubDate>
    <dc:creator>Admin</dc:creator>
    <guid isPermaLink="false">455 at https://yaffs.net</guid>
    </item>
<item>
  <title>Running Yaffs Direct Tests</title>
  <link>https://yaffs.net/running-yaffs-direct-tests</link>
  <description>&lt;span property=&quot;schema:name&quot;&gt;Running Yaffs Direct Tests&lt;/span&gt;
&lt;span rel=&quot;schema:author&quot;&gt;&lt;span lang=&quot;&quot; about=&quot;/user/admin&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Admin&lt;/span&gt;&lt;/span&gt;
&lt;span property=&quot;schema:dateCreated&quot; content=&quot;2012-07-23T00:03:16+00:00&quot;&gt;23 July, 2012 - 1:03am&lt;/span&gt;
</description>
  <pubDate>Mon, 23 Jul 2012 00:03:16 +0000</pubDate>
    <dc:creator>Admin</dc:creator>
    <guid isPermaLink="false">454 at https://yaffs.net</guid>
    </item>
<item>
  <title>Yaffs Direct Interface</title>
  <link>https://yaffs.net/documents/yaffs-direct-interface</link>
  <description>&lt;span&gt;Yaffs Direct Interface&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/admin&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Admin&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;23 July, 2012 - 12:37am&lt;/span&gt;

      &lt;div class=&quot;field field--name-upload field--type-file field--label-hidden field--items&quot;&gt;
              &lt;div class=&quot;field--item&quot;&gt;&lt;span class=&quot;file file--mime-application-pdf file--application-pdf icon-before&quot;&gt;&lt;span class=&quot;file-icon&quot;&gt;&lt;span class=&quot;icon glyphicon glyphicon-file text-primary&quot; aria-hidden=&quot;true&quot;&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&quot;file-link&quot;&gt;&lt;a href=&quot;https://yaffs.net/sites/default/files/downloads/YaffsDirect.pdf&quot; type=&quot;application/pdf; length=256079&quot; title=&quot;Open file in new window&quot; target=&quot;_blank&quot; data-toggle=&quot;tooltip&quot; data-placement=&quot;bottom&quot;&gt;YaffsDirect.pdf&lt;/a&gt;&lt;/span&gt;&lt;span class=&quot;file-size&quot;&gt;250.08 KB&lt;/span&gt;&lt;/span&gt;&lt;/div&gt;
          &lt;/div&gt;
  
            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;
&lt;p&gt;This document describes the Yaffs Direct Interface (YDI), which allows Yaffs to be simply integrated with embedded systems, with or without an RTOS.&lt;/p&gt;
&lt;p style=&quot;page-break-before: always&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;1 Background&lt;/h1&gt;
&lt;p&gt;The purpose of this document is to describe the interfacing of the Yaffs Direct Interface (YDI) as well as to provide sufficient information to allow a preliminary evaluation of Yaffs. This document tries to focus on the issues important to the system integrator without getting too detailed about how Yaffs works. Other documents provide an in-depth discussion of how Yaffs works.&lt;/p&gt;
&lt;h1 class=&quot;western&quot;&gt;2 Licensing&lt;/h1&gt;
&lt;p&gt;Yaffs was originally released for Linux under the GNU Public License (GPL). Various embedded developers soon identified that Yaffs would be ideal for their applications, but were not able to use GPL based code in their systems. Aleph One &lt;span style=&quot;font-style: normal&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;has&lt;/span&gt;&lt;/span&gt; alternative licensing arrangements to support such applications.&lt;/p&gt;
&lt;h1 class=&quot;western&quot;&gt;3 What are Yaffs and Yaffs Direct Interface?&lt;/h1&gt;
&lt;p&gt;Yaffs stands for &lt;i&gt;Yet Another Flash File System&lt;/i&gt;. Yaffs was the first file system designed, from the ground up, for NAND storage.&lt;/p&gt;
&lt;p&gt;In 2002 Aleph One set out to identify file system options for using NAND Flash as a file system. Various file systems available at the time were evaluated and all were found lacking in one way or another. The need for a suitable NAND storage file system was identified and Yaffs was designed to fill that need.&lt;/p&gt;
&lt;p&gt;Although Yaffs was originally designed for NAND flash, it has been used successfully with NOR flash systems and even as a RAM file system. This allows high reliability file systems to be constructed using NOR flash, with a future migration path &lt;span style=&quot;font-weight: normal&quot;&gt;to NAND&lt;/span&gt; flash for higher density and performance.&lt;/p&gt;
&lt;p&gt;Yaffs was originally designed for use with the Linux operating system, but was designed in a very modular way. The operating-system-specific code was kept separate from the main Yaffs file system code. This allows Yaffs to be ported quite cleanly to other operating systems through operating system personality modules. One such personality module is the Yaffs Direct Interface (YDI) which allows Yaffs to be simply integrated with embedded systems, with or without an RTOS. &lt;/p&gt;
&lt;p&gt;Yaffs has been used for many products using various operating systems including Windows CE and various RTOSs, including &lt;span style=&quot;font-weight: normal&quot;&gt;ThreadX, vXworks, pSOS to name just a few.&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;Note that there is a native port of Yaffs to eCOS that does not use YDI. This is supported and distributed by eCocCentric.(http://www.ecoscentric.com/).&lt;/p&gt;
&lt;p&gt;Yaffs2, a more recent release of Yaffs, supports a wider range of NAND flash components including 2k page devices and devices with multi-level cells (MLC), and produces equivalent or better performance. It include Yaffs1 compatibility code so Yaffs1 images still work and migration is quite simple. Yaffs1 or Yaffs2 mode of operation are simply selected by a run-time parameter.&lt;/p&gt;
&lt;p&gt;As well as providing a NAND file system, YDI also provides a RAM emulation layer to allow Yaffs to operate as a RAM file system too. While the RAM emulation is perhaps not as efficient as a dedicated RAM file system, this does allow one well proven file system to use both RAM and flash.&lt;/p&gt;
&lt;h1 class=&quot;western&quot;&gt;4 Why use Yaffs?&lt;/h1&gt;
&lt;p&gt;Yaffs is the first, and perhaps only, file system designed specifically for NAND flash. This means that Yaffs has been designed to work around the various limitations and quirks of NAND flash, as well as exploit the various features of NAND to achieve an effective file system.&lt;/p&gt;
&lt;p&gt;Some features to consider:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Yaffs has been well proven and has been used to ship in &lt;span style=&quot;font-weight: normal&quot;&gt;large volumes in several products using many different operating systems, compilers and processors.&lt;/span&gt;&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs is written in portable C and is endian neutral.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs provides &lt;span style=&quot;font-weight: normal&quot;&gt;bad&lt;/span&gt; &lt;b&gt;&lt;/b&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;block&lt;/span&gt; handling and ECC algorithms to handle deficiencies in NAND flash.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs is a log-structured file system which makes it very robust to corruptions caused by power failures etc.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs has highly optimised and predictable garbage collection strategies. This makes it high performance and very deterministic when compared with similar file systems.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs has a lower memory footprint than most other log-structured flash file systems.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs provides a wide range of POSIX-style file system support including directories, symbolic and hard links etc. through standard file system interface calls.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;Yaffs is h&lt;/span&gt;ighly configurable to work with various flash geometries, various ECC options, caching options etc.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs Direct Interface is simple to integrate in a system – only a few interface functions are required.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs can be used with a wide range of memory technologies.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 class=&quot;western&quot;&gt;5 Source Code and Yaffs Resources &lt;/h1&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;Please note the licensing terms that apply to using the Yaffs code.&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;http://www.yaffs.net/&quot;&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;http://www.yaffs.net&lt;/span&gt;&lt;/a&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-style: normal&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;serves as the hub for all Yaffs information.&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;This document refers to the Yaffs source code extensively.&lt;span style=&quot;font-style: normal&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;and is available via the download link on this site.&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;There are various other documents and a Yaffs mailing list for Yaffs discussions.&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;Consulting services are also available.&lt;/span&gt;&lt;/p&gt;
&lt;h1 class=&quot;western&quot;&gt;6 System Requirements&lt;/h1&gt;
&lt;p&gt;Determining minimum system requirements is often quite difficult. The following are presented as a guideline only. Contact Aleph One for more detailed analysis if required.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Yaffs is endian-neutral and works fine with little-endian and big-endian processors.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Yaffs code has been used successfully with many different 32-bit and 64-bit CPUs including MIPS, 68000, ARM, ColdFire, PowerPC and x86 variants. Yaffs has even been used with various DSP architectures. Yaffs should work with 16-bit CPUs too, but this is generally untested and might need some tuning, depending on compiler options.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Because Yaffs is log structured, RAM is required to build up runtime data structures for acceptable performance. As a rule of thumb, budget approximately 2 bytes per &lt;i&gt;chunk&lt;/i&gt; of NAND flash, where a &lt;i&gt;chunk&lt;/i&gt; is typically one page of NAND. For NAND with 512byte pages, budget approximately 4kbytes of RAM per 1Mbyte of NAND. For 2kbyte page devices budget approximately 1kbyte per 1Mbyte of NAND.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;h1 class=&quot;western&quot;&gt;7 How to integrate Yaffs with an RTOS/Embedded system&lt;/h1&gt;
&lt;p&gt;Yaffs Direct Interface (YDI) wraps Yaffs in a way that is simple to integrate. You need to provide a few functions for Yaffs to use to talk to your hardware and RTOS. Yaffs provides a set of POSIX-compliant functions for applications to use to talk to it.&lt;/p&gt;
&lt;p&gt;In addition to the Yaffs core file system, the YDI has three parts which are each explained in more detail in further sections:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;b&gt;POSIX Application Interface&lt;/b&gt;: This is the POSIX-like interface that the application code uses to access the Yaffs file system. (&lt;span style=&quot;font-family: Times New Roman;&quot;&gt;&lt;i&gt;open, close, read, write, &lt;/i&gt;&lt;/span&gt;etc) &lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;b&gt;RTOS Integration Interface&lt;/b&gt;: These are the functions that must be provided for Yaffs to access the RTOS system resources. (&lt;span style=&quot;font-family: Times New Roman;&quot;&gt;&lt;i&gt;initialise, lock, unlock, get time, &lt;/i&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Times New Roman;&quot;&gt;&lt;i&gt;memory allocation,&lt;/i&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Times New Roman;&quot;&gt;&lt;i&gt;set error, &lt;/i&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Times New Roman;&quot;&gt;&lt;i&gt;etc&lt;/i&gt;&lt;/span&gt;). Note that although we use the term RTOS, the same can be done with other OSs or even with no RTOS at all in a bare-metal system.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;img src=&quot;data:image/png;base64,[encoded data, 27864 characters]&quot; width=&quot;485&quot; height=&quot;530&quot; alt=&quot;image&quot; id=&quot;Object1&quot; /&gt; &lt;b&gt;Flash Device &lt;/b&gt;&lt;b&gt;Interface&lt;/b&gt;: This interface support is where the flash device and appropriate device drivers are installed to provide an access path from Yaffs to the flash device(s). Multiple different devices and device types can be supported simultaneously.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 class=&quot;western&quot;&gt;7.1 Source Files&lt;/h2&gt;
&lt;p&gt;The following source files contain the core file system:&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;71*&quot; /&gt; &lt;col width=&quot;185*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_allocator.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Allocates Yaffs object and tnode structures.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_bitmap.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Block and chunk bitmap handling code.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_checkpointrw.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Streamer for writing checkpoint data&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_ecc.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;1-bit Hamming ECC code&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_guts.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;The major Yaffs algorithms.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_nameval.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Name/value code for handling extended attributes (xattr).&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_nand.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Flash interfacing abstraction.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_packedtags1.c&lt;br /&gt;
  yaffs_packedtags2.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Tags packing code&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_summary.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Code for handling block summaries.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_tagscompat.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Tags compatibility code to support Yaffs1 mode.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_tagsmarshall.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Tags marshalling code.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_verify.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Test verification code.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_yaffs1.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Yaffs1-mode specific code.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_yaffs2.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Yaffs2-mode specific code.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;The Yaffs direct interface is in yaffsfs.c, with the interface functions and structures defined in yaffsfd.h.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;page-break-inside: avoid; width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;72*&quot; /&gt; &lt;col width=&quot;184*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_attribs.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Attribute handling.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_error.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Error reporting code.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffsfs.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Yaffs Direct Interface wrapper code.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_hweight.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Counts the number of hot bits in a byte, word etc.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_qsort.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Qsort used during Yaffs2 scanning&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Example flash drivers, simulators and configurations used for testing are are in direct/test-framework directory. These include:&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;page-break-inside: avoid; width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;72*&quot; /&gt; &lt;col width=&quot;184*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;nanddrv.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A NAND driver layer that performs the commands to access NAND flash in a rudimentary manner. This code should work on many styles of CPU with little modification.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_nanddrv.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A wrapper around the NAND driver which plugs it into Yaffs.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;nandsim.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A NAND simulator layer that works with a nandstore_xxx backing store. This simulates a NAND chip.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;nandstore_file.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A storage backend for a NAND simulator that stores the data to file.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;nandsim_file.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A wrapper around nandsim.c and nandstore_file.c which makes a NAND simulator that saves its data in a file.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_nandsim_file.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A wrapper which creates a nand simulator instance, hooks up the yaffs NAND driver and then adds it to yaffs for use.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_nor_drv.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;ol&gt;
 &lt;/ol&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_m18_drv.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A driver for Intel M18-style NOR flash.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_osglue.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;An OS glue layer example used in the test harness.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Example and testing build files:&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;71*&quot; /&gt; &lt;col width=&quot;185*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;dtest.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A test harness. Also has sample code that can be used for better understanding of how some function calls work.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffscfg2k.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;A test configuration.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 28%;&quot;&gt;
 &lt;p&gt;yaffs_fileem.c&lt;br /&gt;
  yaffs_fileem2k.c&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 72%;&quot;&gt;
 &lt;p&gt;Nand flash simulation using a file as backing store.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Further testing files are in direct/tests and direct/python.&lt;/p&gt;
&lt;h2 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;7.2 Integrating the POSIX Application Interface&lt;/h2&gt;
&lt;p&gt;The application interface is defined in yaffsfs.h. These provide a POSIX file system interface. For the most part, this interface consists of the standard clib function names prefixed with &lt;code class=&quot;western&quot;&gt;yaffs_&lt;/code&gt;. For example, &lt;code class=&quot;western&quot;&gt;yaffs_open(), yaffs_close()&lt;/code&gt; etc.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;There is a lot of flexibility in how these functions are used and the system integrator needs to determine the best strategy for the system.&lt;/p&gt;
&lt;p&gt;These functions can be used directly, with the code written using these names. For example&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;int main(...)&lt;br /&gt;
{&lt;br /&gt;
// initialisation&lt;br /&gt;
f = yaffs_open(...);&lt;br /&gt;
yaffs_read(f,...);&lt;br /&gt;
yaffs_close(f);&lt;br /&gt;
}&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;The &lt;span style=&quot;font-family: Times New Roman;&quot;&gt;yaffs&lt;/span&gt; functions can also be wrapped in some way to allow existing code to use yaffs without modification. For example:&lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0cm; orphans: 0; widows: 0; page-break-before: auto; page-break-after: avoid&quot;&gt;&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;#define open(path, oflag, mode) yaffs_open(path, oflag, mode)&lt;br /&gt;
..&lt;br /&gt;
&lt;br /&gt;
int main(...)&lt;br /&gt;
{&lt;br /&gt;
// initialisation&lt;br /&gt;
f = open(...);&lt;br /&gt;
read(f,...);&lt;br /&gt;
close(f);&lt;br /&gt;
}&lt;/code&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0cm; orphans: 0; widows: 0; page-break-before: auto&quot;&gt;&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;A more complex approach that can be used if more than one file-system is used is to provide redirection functions. For example:&lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0cm; orphans: 0; widows: 0; page-break-before: auto; page-break-after: avoid&quot;&gt;&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;int open(const char *path,...)&lt;br /&gt;
{&lt;br /&gt;
// Determine which file system is being used&lt;br /&gt;
&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;i&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;f(it_is_a_yaffs_path(path))&lt;br /&gt;
return yaffs_open(...);&lt;br /&gt;
else {&lt;br /&gt;
// Do something else&lt;br /&gt;
}&lt;br /&gt;
}&lt;/code&gt;&lt;/p&gt;
&lt;p style=&quot;margin-left: 1.25cm; margin-bottom: 0cm; page-break-inside: avoid; orphans: 0; widows: 0; page-break-before: auto; page-break-after: auto&quot;&gt;&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Some RTOS&#039;s provide a flexible way to integrate file systems in which case YDI can typically use these interfaces to access yaffs file systems.&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;8 RTOS Integration Interface&lt;/h1&gt;
&lt;p&gt;Before Yaffs can be used, it needs to be integrated with the system and configured so that the correct actions are performed.&lt;/p&gt;
&lt;p&gt;To do this, you need to modify the configuration file. An example configuration file is presented in &lt;span style=&quot;font-family: Bitstream Vera Sans;&quot;&gt;&lt;span style=&quot;font-family: Times New Roman;&quot;&gt;yaffscfg.c and yaffscfg2k.c.&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;This is a relatively straight forward process and defines the RTOS access functions.&lt;/p&gt;
&lt;p&gt;The RTOS access functions are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;void yaffsfs_SetError(int err)&lt;/code&gt;: Called by Yaffs to set the system error.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;void yaffsfs_Lock(void)&lt;/code&gt;: Called by Yaffs to lock Yaffs from multi-threaded access.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;void yaffsfs_Unlock(void)&lt;/code&gt;: Called by Yaffs to unlock Yaffs.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;u32 yaffsfs_CurrentTime(void)&lt;/code&gt;: Get current time from RTOS.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;void *yaffsfs_malloc(size_t size)&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;: Called to allocate memory.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;void yaffsfs_free(void *ptr)&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;: Called to free memory.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;void yaffsfs_&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;OS&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;Initialisation(void)&lt;/code&gt;: Called to initialise RTOS context.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;void yaffs_bug_fn(const char *file_name, int line_no)&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;: Function to report a bug.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;int yaffsfs_CheckMemRegion(const void *addr, size_t size, int writ&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;e_request&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;) : Function to check if accesses to a memory region is valid. This function must return zero if the test passes and negative if it fails.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;If Yaffs is being used in a multi-threaded environment, then typically &lt;code class=&quot;western&quot;&gt;yaffs_LocalInitialisation()&lt;/code&gt; will initialise a suitable RTOS semaphore and &lt;code class=&quot;western&quot;&gt;yaffs_Lock()&lt;/code&gt; and &lt;code class=&quot;western&quot;&gt;yaffs_Unlock()&lt;/code&gt; will call the appropriate functions to lock and release the semaphore.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_CurrentTime()&lt;/code&gt; can be any time increment of use to the system. If this is not required, then it is fine to just use a function that is hard-wired to return zero.&lt;/p&gt;
&lt;p&gt;Before the application code uses Yaffs, the &lt;code class=&quot;western&quot;&gt;yaffs&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;fs&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;_&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;OSInitialisation&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;()&lt;/code&gt; function must be called.&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;yaffsfs_CheckMemRegion()&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-size: 12pt; font-size: medium; font-size: medium;&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;is used to check addresses passed to the various yaffs_xxx functions (yaffs_open(), yaffs_read() etc)). If the function returns -1, then the yaffs_xxx function will return -EFAULT rather than attempt to dereference the address and crash.&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;font-weight: normal&quot;&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-size: 12pt; font-size: medium; font-size: medium;&quot;&gt;An implementation might do something like:&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;font-weight: normal&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;int yaffsfs_CheckMemRegion(const void addr, size_t size, &lt;br /&gt;
int write_&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;request&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;) &lt;br /&gt;
{&lt;br /&gt;
u32 uaddr&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;b&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;= (u32) addr;&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;u32 uaddrt = uaddrb + size -1;&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&lt;br /&gt;
if( uaddr&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;b&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&amp;gt;= stack_bottom &amp;amp;&amp;amp; uaddr&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;b&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&amp;lt;= stack_top &amp;amp;&amp;amp;&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;uaddrt &amp;gt;= stack_bottom &amp;amp;&amp;amp; uaddrt &amp;lt;= stack_top)&lt;br /&gt;
return 0; /* &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;r/w &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;access is OK */&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&lt;br /&gt;
if( uaddr&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;b&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&amp;gt;= &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;heap&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;_bottom &amp;amp;&amp;amp; uaddr&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;b&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&amp;lt;= &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;heap&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;_top &amp;amp;&amp;amp;&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;uaddrt &amp;gt;= heap_bottom &amp;amp;&amp;amp; uaddrt &amp;lt;= heap_top)&lt;br /&gt;
return 0; /* &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;r/w&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;access is OK /&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&lt;br /&gt;
if( !&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;write_request &amp;amp;&amp;amp;&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;uaddr&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;b&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&amp;gt;= &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;rom&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;_bottom &amp;amp;&amp;amp; uaddr&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;b&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&amp;lt;= &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;rom&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;_top &amp;amp;&amp;amp;&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;uaddrt &amp;gt;= rom_bottom &amp;amp;&amp;amp; uaddrt &amp;lt;= rom_top)&lt;br /&gt;
return 0; / &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;read &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;access is OK /&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;return -1; /* Bad access */&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;&lt;br /&gt;
&lt;br /&gt;
}&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;9 Yaffs NAND Model&lt;/h1&gt;
&lt;p&gt;Before defining the flash integration interface, it is important to understand the model and corresponding nomenclature used throughout Yaffs and its documentation.&lt;/p&gt;
&lt;p&gt;Yaffs uses a fairly abstract model for NAND flash. This allows a lot of flexibility in the way it can be used.&lt;/p&gt;
&lt;p&gt;Yaffs is designed for NAND flash and makes the following assumptions and definitions:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;The flash is arranged in &lt;i&gt;&lt;b&gt;blocks&lt;/b&gt;&lt;/i&gt;. Each block is the same size and comprises an integer number of &lt;span style=&quot;font-style: normal&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;chunks&lt;/span&gt;&lt;/span&gt;. Each block is treated as a single erasable item. A block contains a number of chunks.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;A &lt;i&gt;&lt;b&gt;chunk&lt;/b&gt;&lt;/i&gt; equates to the allocation units of flash. For Yaffs1, each chunk equates to a 512-byte or larger NAND page (that is, a 512-byte or larger data portion and a 16-byte spare area). For Yaffs2, a chunk will typically be larger (eg. on 2k page devices, a chunk will typically be a single 2k page: 2kbytes of data and 64 bytes of spare). Yaffs2 is capable of working with smaller chunk sizes by using inband tags.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;All accesses (reads and writes) are page chunk aligned. Some reads might only read the spare area where the tags are kept.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;When programming a NAND flash, only the zero bits in the pattern being programmed are relevant, and one bits are &amp;quot;don&#039;t care&amp;quot;. For example, if a byte already contains the binary pattern b1010, then programming b1001 will result in the pattern which is the logical AND of these two patterns ie. b1000. This is different to NOR flash which would typically abort the attempt to convert a 0 into a 1.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Yaffs ide&lt;span style=&quot;font-weight: normal&quot;&gt;ntifies&lt;/span&gt; blocks by their block number and chunks by the chunk Id. A chunk Id is calculated as:&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;chunkId = block_id * chunks_per_block + chunk_offset_in_block&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;Yaffs treats a blank (0xFF filled) block as being free or erased. Thus, the equivalent of formatting for a Yaffs partition is to erase all the blocks that are not bad.&lt;/p&gt;
&lt;p&gt;Yaffs2 has a generalised tags interface to provide better flexibility to cater for a wider range of devices with larger pages and stricter programming limitations. Yaffs2 thus handles more abstract constructs than Yaffs1 and, in older versions of Yaffs, more effort was required to interface to the NAND.&lt;/p&gt;
&lt;p&gt;In newer versions of Yaffs, the tags management has been abstracted out of the driver. This makes the driver interface far simpler.&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;9.1 Formatting&lt;/h2&gt;
&lt;p&gt;Yaffs treats erased blocks as empty. That makes it really easy to “format” a device: just erase it.. Note that this should be done while the partition is not mounted.&lt;/p&gt;
&lt;p&gt;Unmounting will not normally work when the file system is busy (eg. files are open), Some extra non-standard unmount options are provided to enable an unmount to be forced. Note that using these will break any current handles and you will no longer be able to use open files.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-size: 12pt; font-size: medium; font-size: medium;&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;There is a &lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;yaffs_format() &lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-size: 12pt; font-size: medium; font-size: medium;&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;function that will take care of the details.&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;9.2 NAND Model considerations for Yaffs1&lt;/h2&gt;
&lt;p&gt;The historical Yaffs1 tags structure was laid out in accordance with the SmartMedia specification for use with 512-byte pages. There is now much more flexibility in the way things can be configured.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Yaffs1 is capable of being used with a variety of memory layouts so long as the flash supports the ability to overwrite the tags area to set the deletion marker to zero.&lt;/p&gt;
&lt;p&gt;If the yaffs_dev&#039;s use_nand_ecc field is not set, then yaffs will perform the ECC calculations. If this is set then yaffs will expect the NAND driver to do any required ECC checks. On devices that are not using ECC, for example NOR, set use_nand_ecc=1 and then don&#039;t do any ECC anyway.&lt;/p&gt;
&lt;p&gt;The Yaffs1 flash model expects an area of 16 spare bytes, some of which are used for tags. The mapping between the spare bytes and the usage of the bytes is specified in yaffs_packedtags1.c&lt;/p&gt;
&lt;p&gt;The Yaffs1 model has been used in many NOR-based systems. One particularly instructive example is in yaffs_nor_drv.c which implements a driver for Yaffs1 mode on CFI-style NOR flash. This does not use ECC but uses checksumming instead.&lt;/p&gt;
&lt;p&gt;The yaffs_dev structure has a yaffs_driver structure which holds the function pointers to the driver. For Yaffs1 mode of operations the following are required:&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;page-break-inside: avoid; width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;77*&quot; /&gt; &lt;col width=&quot;179*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_write_chunk_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Write a data chunk&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_read_chunk_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Read a data chunk.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_erase_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Erase a block&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_initialise_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Initialisation.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_deinitialise_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;De-initialise&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;These functions are described later.&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;9.3 NAND Model for Yaffs2&lt;/h2&gt;
&lt;p&gt;The Yaffs2 interface is far more flexible than Yaffs1, but that means a bit more effort must be done in the driver. In particular:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;There is is no standard spare area/ECC layout. The driver must handle all the layout of the spare area and ECC handling.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;There is not a standard implementation for bad block markers. Thus, the driver must provide functions for checking and marking bad blocks.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The yaffs_driver structure for Yaffs2 mode requires the following functions:&lt;/p&gt;
&lt;p style=&quot;margin-bottom: 0cm; orphans: 0; widows: 0; page-break-before: auto&quot;&gt;&lt;br /&gt;
&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;page-break-inside: avoid; width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;77*&quot; /&gt; &lt;col width=&quot;179*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_write_chunk_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Write a data chunk&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_read_chunk_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Read a data chunk.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_erase_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Erase a block&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_mark_bad_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Mark a block bad&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_check_bad_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Check bad block status of a block.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_initialise_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;Initialisation.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 30%;&quot;&gt;
 &lt;p&gt;drv_deinitialise_fn&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 70%;&quot;&gt;
 &lt;p&gt;De-initialise&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;9.4 Overview of flash driver function&lt;/h2&gt;
&lt;p&gt;The best way to understand how to write these functions is to look at the example drivers.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int (*drv_write_chunk_fn) (struct yaffs_dev *dev, int nand_chunk, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;const u8 *data, int data_len, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;const u8 *oob, int oob_len)&lt;/p&gt;
&lt;p&gt;This function writes the specified chunk data and oob/spare data to flash.&lt;/p&gt;
&lt;p&gt;This function should return YAFFS_OK on success or YAFFS_FAIL on failure.&lt;/p&gt;
&lt;p&gt;If this is a Yaffs2 device, or Yaffs1 with use_nand_ecc set, then this function must take care of any ECC that is required.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int (*drv_read_chunk_fn) (struct yaffs_dev *dev, int nand_chunk, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;u8 *data, int data_len, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;u8 *oob, int oob_len,&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;enum yaffs_ecc_result *ecc_result)&lt;/p&gt;
&lt;p&gt;This function reads the specified chunk data and oob/spare data from flash.&lt;/p&gt;
&lt;p&gt;This function should return YAFFS_OK on success or YAFFS_FAIL on failure.&lt;/p&gt;
&lt;p&gt;If this is a Yaffs2 device, or Yaffs1 with use_nand_ecc set, then this function must take care of any ECC that is required and set the ecc_result.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int (*drv_erase_fn) (struct yaffs_dev *dev, int block_no) &lt;/p&gt;
&lt;p&gt;This function erases the specified block.&lt;/p&gt;
&lt;p&gt;This function should return YAFFS_OK on success or YAFFS_FAIL on failure.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int (*drv_mark_bad_fn) (struct yaffs_dev *dev, int block_no); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int (*drv_check_bad_fn) (struct yaffs_dev *dev, int block_no); &lt;/p&gt;
&lt;p&gt;These functions are only required for Yaffs2 mode. They mark a block bad or check if it is bad.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int (*drv_initialise_fn) (struct yaffs_dev *dev); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int (*drv_deinitialise_fn) (struct yaffs_dev *dev); &lt;/p&gt;
&lt;p&gt;These functions provide hooks for initialising or deinitialising the flash driver.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;10 Configuration and flash driver installation&lt;/h1&gt;
&lt;p&gt;For an example of how to do the configuration, refer to yaffs_cfg2k.c and one of the drivers such as yaffs_nand_drv.c&lt;/p&gt;
&lt;p&gt;The old mechanism was static and required a table of devices that was installed at start up. This mechanism had shortcomings – in particular it broke modularity and did not allow devices to be added dynamically.&lt;/p&gt;
&lt;p&gt;Things are different now. As any time, a yaffs_dev structure can be configured and then registered with Yaffs by using the yaffs_add_device() function.&lt;/p&gt;
&lt;p&gt;A yaffs_dev structure has two parts which must be configured before yaffs_add_device() is called: the paramers (dev-&amp;gt;param) and the driver (dev-&amp;gt;drv). The driver configuration (plugging in the driver functions) has already been described above, so we will now look at the yaffs parameters.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;The yaffs_param structure must be set before the yaffs_dev is added with yaffs_add_device() and should not be modified after that.&lt;/p&gt;
&lt;p&gt;The params are defined in the Yaffs Tuning Document.&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;11 Using the POSIX file system interface&lt;/h1&gt;
&lt;p&gt;This section is directed to readers that might not be very familiar with accessing a file system via POSIX and POSIX-like interfaces.&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.1 Difference to Windows POSIX-like interfaces&lt;/h2&gt;
&lt;p&gt;MSDOS and Windows provide a POSIX-lke interface. If you are familiar with this then that will help you. There are are however some slight differences, most importantly:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Windows has no concept of links and has a 1:1 mapping between file names and files.POSIX supports files with zero, one or many names. Refer to the sections on linking and unlinking files. For instance POSIX allows you to unlink a file (ie delete the name for a file) while it is still in use. You can continue to read/write the file but it will be deleted as soon as the last file handle to the file is closed. Windows, on the other hand, does not allow you to unlink a file while it is in use.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Windows names drives with a letter. POSIX has no drive letters. The whole POSIX file system is in a single directory tree.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Directories and “folders” are the same thing.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 class=&quot;western&quot;&gt;11.2 Fundamental concepts&lt;/h2&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;width: 642px; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;126&quot; /&gt; &lt;col width=&quot;499&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;File&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;A file is an object that is stored in the file system. yaffs supports the following file types:&lt;/p&gt;
 &lt;p&gt;A regular file is a sequence of bytes stored in the file system.&lt;/p&gt;
 &lt;p&gt;A directory holds links to other files.&lt;/p&gt;
 &lt;p&gt;A symbolic link holds a name to another file.&lt;/p&gt;
 &lt;p&gt;A special file holds device ids or similar information.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;Directory&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;This is a structure that holds links and allows a file to be found by name. Note that a single file may have many links(ie names) and many be found in many places in the directory structure.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;Link&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;This is a name that allows the file to be found. There are two types of link: real links (sometimes called hard links) and symbolic (or soft) links. &lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;Handle&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;A file handle provides a context from which a file can be accessed and manipulated. A handle has a current file position pointer which points to where the file is being read or written. Multiple handles can simultaneously access a single file.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;File mode&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;The mode is the set of flags that define the type of file as well as the current permissions associated with the file.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;Path&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;This is a string that defines the directories and file name. For example:&lt;/p&gt;
 &lt;p&gt;“/data/direct-1/file1”&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;File metadata&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;This is the information about the file, excluding the file contents. The metadata includes the name, mode, size and other details.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;Mount,&lt;br /&gt;
  partition,&lt;br /&gt;
  file system&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;These terms all refer to a single mounted flash area. Each mount is hooked into a common directory structure.&lt;br /&gt;
  The term file system can sometimes be confusing because it is used both for a single mounted partition as well as the the file system code. In other words, we might say that both “/boot” is a file system and might also say that yaffs is a file system.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 126px;&quot;&gt;
 &lt;p&gt;inode number&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 499px;&quot;&gt;
 &lt;p&gt;The inode number is a unique number that identifies the object within the mount. Note that inodes are not unique between two or more mounts. There is no way to reach a file by inode, only via its links.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.3 Error code&lt;/h2&gt;
&lt;p&gt;Most functions result in error codes if the function does not execute successfully. In these cases yaffs calls a function called &lt;code class=&quot;western&quot;&gt;yaffs_SetError()&lt;/code&gt; with the error value. This function can be configured to deliver the error into the system&#039;s error mechanism.&lt;/p&gt;
&lt;p&gt;In the case of functions that return integers, a returned value smaller than 0 indicates an error occurred. Functions returning pointers will return NULL if an error occurred.&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.4 Links – the hard kind (not symbolic links)&lt;/h2&gt;
&lt;p&gt;At first we&#039;re just considering real links and not symbolic links. Sometimes real links are also called hard links to differentiate them from symbolic links (which are sometimes called soft links).&lt;/p&gt;
&lt;p&gt;The difference between links and files is subtle and can be confusing. Briefly:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;a file is the stored object in the file system&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;the link is how it is hooked into the directory structure.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;The first link to a file is created by using the file creation calls: &lt;code class=&quot;western&quot;&gt;yaffs_open()&lt;/code&gt;, &lt;code class=&quot;western&quot;&gt;yaffs_mknod()&lt;/code&gt;, &lt;code class=&quot;western&quot;&gt;yaffs_symlink()&lt;/code&gt; and &lt;code class=&quot;western&quot;&gt;yaffs_mkdir()&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;A link can be destroyed by using the &lt;code class=&quot;western&quot;&gt;yaffs_unlink()&lt;/code&gt; function. Directories are destroyed using the &lt;code class=&quot;western&quot;&gt;yaffs_rmdir()&lt;/code&gt; function (oh, and the directory must be empty).&lt;/p&gt;
&lt;p&gt;Once a file is both unused (there are no handles open to it) and there are no links to it it is then deleted.&lt;/p&gt;
&lt;p&gt;A link can be renamed by using the &lt;code class=&quot;western&quot;&gt;yaffs_rename()&lt;/code&gt; function.&lt;/p&gt;
&lt;p&gt;A file may have many links. These may be created using the &lt;code class=&quot;western&quot;&gt;yaffs_link()&lt;/code&gt; function. All the links access the same file and there is no one link that is considered “the real link” and others being “the duplicate link”. All links to a file have the same priority. If you look at the inode number for “a” and for “b” then they will be the same because they are refering to exactly the same file.&lt;/p&gt;
&lt;p&gt;Thus:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;If we start with a file called “a” and then call &lt;code class=&quot;western&quot;&gt;yaffs_link(“a”, “b”)&lt;/code&gt; we now have two links to the same file. We can&#039;t tell them apart.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;If we now unlink “a”, the file still exists under the link “b”.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;If we now unlink “b” the file will no longer be linked. If there is a handle open to the file then we can still access the file through the handle and continue to read or modify the file. If there is no link to the file it is deleted.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;If an unlinked file was kept alive because of a handle being open, the file will not show up in the directory structure (because it has no link) and will be deleted as soon as the handle is closed (or if the file system is unmounted).&lt;/p&gt;
 &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;There are some limitations in how links are used:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;The existing file you are linking to must exist.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;The file you are linking to must be in the same mount (partition) as the link you are creating.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;You cannot create a link to a directory because this would allow the creation of recursive loops.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;The new link name must not exist.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.5 Symbolic links&lt;/h2&gt;
&lt;p&gt;Now that you understand how hard links work, we&#039;ll introduce symbolic (or soft) links.&lt;/p&gt;
&lt;p&gt;A symbolic link holds an alias for a different object. When you use that symbolic link in a path the alias is used instead. To that extent symbolic link and hard links are the same.&lt;/p&gt;
&lt;p&gt;You can remove symbolic links with the &lt;code class=&quot;western&quot;&gt;yaffs_unlink()&lt;/code&gt; function, just like hard links.&lt;/p&gt;
&lt;p&gt;There are, however, some important differences. A symbolic link only does its linking function when the path is being evaluated and thus:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;The file you are creating an alias to does not have to exist.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;The file you are creating an alias to does not have to be in the same mount.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;You can create symbolic links to directories.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;A symbolic link will not keep a file alive by itself. Only a hard link can do that.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Thus:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;If we start with a file called “a” and then call &lt;code class=&quot;western&quot;&gt;yaffs_symlink(“a”, “b”)&lt;/code&gt; we now have one link to the file called “a” and a symbolic link aliasising from “b” to “a”.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;If we use &lt;code class=&quot;western&quot;&gt;yaffs_open(“a”)&lt;/code&gt; or &lt;code class=&quot;western&quot;&gt;yaffs_open(“b”)&lt;/code&gt; they will open the same file. The path resolution mechanism substitutes in the alias and so will look up “a”. The same applies to almost all functions that takes a path, such as &lt;code class=&quot;western&quot;&gt;yaffs_truncate()&lt;/code&gt;, &lt;code class=&quot;western&quot;&gt;yaffs_stat()&lt;/code&gt; etc. The only exceptions are &lt;code class=&quot;western&quot;&gt;yaffs_lstat()&lt;/code&gt; and &lt;code class=&quot;western&quot;&gt;yaffs_readlink()&lt;/code&gt; which will treat the path as pointing to the symbolic link and not the file.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;You can tell “a” and “b” apart by using &lt;code class=&quot;western&quot;&gt;yaffs_lstat()&lt;/code&gt;. &lt;code class=&quot;western&quot;&gt;yaffs_lstat(“a”)&lt;/code&gt; will show the information for file “a”. &lt;code class=&quot;western&quot;&gt;yaffs_lstat(“b”)&lt;/code&gt; will show the information for the symbolic link itself. Note the difference with hard links. With hard links &lt;code class=&quot;western&quot;&gt;yaffs_lstat(“a”)&lt;/code&gt; and &lt;code class=&quot;western&quot;&gt;yaffs_lstat(“b”)&lt;/code&gt; would show the same results since they are EXACTLY the same thing being referenced.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;If we now unlink “a”. then the file is no longer linked and will no longer be accessible from “b”. Note the difference with hard links.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.6 Handle-based file handling&lt;/h2&gt;
&lt;p&gt;A handle is file accessor that allows us to access the contents of a regular file. The handle identifies the file being accessed as well as a position pointer tracking where the next read or write operation will take place.&lt;/p&gt;
&lt;p&gt;A handle is identified by an integer of value 0 or greater.&lt;/p&gt;
&lt;p&gt;A handle is created by using the &lt;code class=&quot;western&quot;&gt;yaffs_open()&lt;/code&gt; call and returns the handle value. If the handle could not be created then a negative value is returned and the yaffs error code is set.&lt;/p&gt;
&lt;p&gt;A handle remains valid until the handle is closed by &lt;code class=&quot;western&quot;&gt;yaffs_close()&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;The &lt;code class=&quot;western&quot;&gt;yaffs_open()&lt;/code&gt; call takes three parameters:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;name: Full path name of the file being opened.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;access flags: Flags being used to open this handle&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;creation mode: Mode flags used when creating a file.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The access flags are one or more of:&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;59*&quot; /&gt; &lt;col width=&quot;197*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;O_CREAT&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;Create file if it does not already exist.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;O_EXCL&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;Only use with O_CREAT. Create file if it does not exist. If the file already exists then fail.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;O_TRUNC&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;If the file exists, and opening with write access, then truncate the file to zero bytes long.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;O_APPEND&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;Regardless of the handle position, always write to the end of the file.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;O_RDWR&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;Open for read/write access.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;O_WRONLY&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;Open for write access and no read access.&lt;/p&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;0 (zero)&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;If neither O_RDWR or O_WRONLY is set then the file will be opened for read-only access.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Where they are not mutually exclusive, these flags are typically combined. For example:&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;O_CREAT | O_TRUNC | O_RDWR&lt;/code&gt; : Create a new file if it does not exist otherwise if the file already exists then truncate to zero length. Typically used to overwrite a file or create if it does not already exist.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;O_CREAT | OEXCL | O_WRONLY&lt;/code&gt; : Create a new file, opening it for write only. Fails if file already exists.&lt;/p&gt;
&lt;p&gt;There are three mode flags that can be controlled or set. These flags may be set by the open that creates the file or later by the &lt;code class=&quot;western&quot;&gt;yaffs_chmod()&lt;/code&gt;.&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;59*&quot; /&gt; &lt;col width=&quot;197*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;S_IREAD&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;The file may be opened for read access.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;S_IWRITE&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;The file may be opened for write access.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 23%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;S_IEXEC&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 77%;&quot;&gt;
 &lt;p&gt;The file may be opened for execution. This is not enforced by yaffs.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Once you have opened a handle you can then do various operations on the file.&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;width: 605px; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;248&quot; /&gt; &lt;col width=&quot;339&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_close(handle)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Close the handle. It is no longer usable.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_fsync(handle)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Flush out any cached writes to the file, as well as the file meta-data.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_datasync(handle)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Same as yaffs_fsync() but no file metadata.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_flush(handle)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Same as yaffs_fsync()&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_dup(handle)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Duplicates a handle.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_lseek(handle, offset, whence)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Set the handle read/write position. Note that this does not modify the file. You can seek past the end of the file. This does not modify the file size.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_ftruncate(handle, size)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Change the file size. It can be made bigger or smaller. This does not change the handle read/write position.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_fstat(handle, buf)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Get file status.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_fchmod(handle, mode)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Change the file mode.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;&lt;br /&gt;
  &lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_read(handle, buffer, nbytes)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Read data from file at file pointer and update pointer.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_pread(handle, buffer, nbytes, position)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Read data from file at specified position. Does not modify file pointer&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_write(handle, buffer, nbytes)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Write data to file at file pointer and update pointer.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 248px;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_pread(handle, buffer, nbytes, position)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 339px;&quot;&gt;
 &lt;p&gt;Write data to file at specified position. Does not modify file pointer&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.7 Changing file size&lt;/h2&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_truncate(path, newSize)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_ftruncate(handle, newSize)&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;These change a file&#039;s size. Note that truncating does not just mean make the file smaller. The file can also be made larger.&lt;/p&gt;
&lt;p&gt;Yaffs does not store bytes that it does not need to. If you use truncate to make a file larger then this will not necessarily occupt more flash space.&lt;/p&gt;
&lt;p&gt;See also &lt;code class=&quot;western&quot;&gt;yaffs_lseek()&lt;/code&gt; too. Note that &lt;code class=&quot;western&quot;&gt;yaffs_lseek() &lt;/code&gt;only changes the position of the write pointer and does not impact on the file size unless the file is written.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.8 Getting/setting information about files&lt;/h2&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_chmod(path, mode)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_fchmod(handle, mode)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_access(path,amode)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_stat(path, struct yaffs_stat *buf) &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_fstat(handle, struct yaffs_stat *buf)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_lstat(path, struct yaffs_stat *buf)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_readlink(path, buf, bufsize)&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;The chmod calls allow you to set different mode flags for the file. These can only be used to manipulate the permissions flags and not change the mode flags relating to the type of file.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_access() &lt;/code&gt;tests that the file can be accessed in the specified mode. This call returns zero on success and -1 is returned&lt;/p&gt;
&lt;p&gt;amode is a bitmask of the following values:&lt;/p&gt;
&lt;table cellpadding=&quot;4&quot; style=&quot;width: 100%; border-spacing: 0px;&quot;&gt;
&lt;col width=&quot;43*&quot; /&gt; &lt;col width=&quot;213*&quot; /&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: 1px solid #000000; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0.1cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 17%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;R_OK&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border: 1px solid #000000; padding: 0.1cm; width: 83%;&quot;&gt;
 &lt;p&gt;Check read is OK&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 17%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;W_OK&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 83%;&quot;&gt;
 &lt;p&gt;Check write is OK&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 17%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;X_OK&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 83%;&quot;&gt;
 &lt;p&gt;Check execute is OK.&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;tr valign=&quot;top&quot;&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: none; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0cm; width: 17%;&quot;&gt;
 &lt;p&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;code class=&quot;western&quot;&gt;0 (zero)&lt;/code&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;
  &lt;/td&gt;
 &lt;td style=&quot;border-top: none; border-bottom: 1px solid #000000; border-left: 1px solid #000000; border-right: 1px solid #000000; padding-top: 0cm; padding-bottom: 0.1cm; padding-left: 0.1cm; padding-right: 0.1cm; width: 83%;&quot;&gt;
 &lt;p&gt;Just checks the file exists&lt;/p&gt;
  &lt;/td&gt;
&lt;/tr&gt;
&lt;/table&gt;
&lt;p&gt;These can be combined.&lt;/p&gt;
&lt;p&gt;For example:&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;if(yaffs_access(path, R_OK | W_OK) == 0)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;the file exists and can be read and written&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;if(yaffs_access(path, 0) == 0)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;the file exists&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;The stat calls retrieve a yaffs_stat structure of data which is defined in yaffsfs.h. There are three versions:&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_fstat&lt;/code&gt;: Takes a handle.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_stat&lt;/code&gt;: Takes a path name and follows symbolic links.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_lstat&lt;/code&gt;: Takes a path but does not follow symbolic links.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Thus, if path is a symbolic link, &lt;code class=&quot;western&quot;&gt;yaffs_fstat() &lt;/code&gt;will give information on the file that the link points to while &lt;code class=&quot;western&quot;&gt;yaffs_lstat()&lt;/code&gt; will give information about the link itself.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_readlink()&lt;/code&gt; will read the read the link value into the buffer provided. For example:&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_symlink(“target”,”/link”); /* create a link called link to target */&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_readlink(“/link”,buffer,10); /* now buffer contains “target” */&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.9 Changing the directory structure and names&lt;/h2&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_open(path, flags, mode)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_mkdir(path, mode)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_symlink(targetPath, linkPath)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_mknod(pathname, mode, dev)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_link(existingPath, newath)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_unlink(path)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_rmdir(path)&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_rename(oldPath, newPath)&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Files of various types, and their first link, are created via the &lt;code class=&quot;western&quot;&gt;yaffs_open()&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-weight: normal&quot;&gt;,&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;span style=&quot;font-family: Courier New, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;/span&gt;&lt;/span&gt;&lt;code class=&quot;western&quot;&gt;yaffs_mkdir()&lt;/code&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;, &lt;/span&gt;&lt;/span&gt;&lt;code class=&quot;western&quot;&gt;yaffs_symlink()&lt;/code&gt; and &lt;code class=&quot;western&quot;&gt;yaffs_mknod()&lt;/code&gt;&lt;span style=&quot;font-family: Liberation Serif, serif;&quot;&gt;&lt;span style=&quot;font-size: 12pt; font-size: medium; font-size: medium;&quot;&gt;&lt;/span&gt;&lt;/span&gt;functions.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_link()&lt;/code&gt; can be used to create subsequent links to files. Note that you cannot create a link to a directory.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_rename()&lt;/code&gt; allows you to rename a link. Note that renaming one link over another link is an atomic operation. That means that even if the operation is interrupted by a power failure, the result will either complete or not happen at all. If the target link is for a directory, then the rename will only work if the target directory is empty.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.10 Searching directories&lt;/h2&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_DIR *yaffs_opendir(const YCHAR *dirname) ; &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;struct yaffs_dirent *yaffs_readdir(yaffs_DIR *dirp) ; &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;void yaffs_rewinddir(yaffs_DIR *dirp) ; &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;int yaffs_closedir(yaffs_DIR *dirp) ; &lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Searching is performed by the following sequence of operations:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Open the directory for reading with &lt;code class=&quot;western&quot;&gt;yaffs_opendir()&lt;/code&gt;.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Iterate through the entries in the directory using &lt;code class=&quot;western&quot;&gt;yaffs_readdir()&lt;/code&gt;. Each read will advance the directory read position.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;You can reset to the start of the directory with &lt;code class=&quot;western&quot;&gt;yaffs_rewinddir()&lt;/code&gt;.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Close the directory when finished with &lt;code class=&quot;western&quot;&gt;yaffs_closedir()&lt;/code&gt;.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;h2 class=&quot;western&quot;&gt;11.11 Searching directories (fd interface)&lt;/h2&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;int &lt;/code&gt;&lt;code class=&quot;western&quot;&gt;yaffs_open(const YCHAR *dirname, &lt;/code&gt;&lt;code class=&quot;western&quot;&gt;O_RDONLY, 0&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;) ; &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;struct yaffs_dirent *yaffs_readdir_&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;fd&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;(&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;int fd&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;) ; &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;void yaffs_rewinddir_&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;fd&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;(&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;int fd&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;) ; &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;int yaffs_close(&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;int fd&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;) ; &lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;This is not a POSIX interface, but provides an alternate interface for reading directories.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Searching is performed by the following sequence of operations:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Open the directory for reading with &lt;code class=&quot;western&quot;&gt;yaffs_open( &lt;/code&gt;&lt;code class=&quot;western&quot;&gt;name, O_RDONLY, 0&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;)&lt;/code&gt;.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Iterate through the entries in the directory using &lt;code class=&quot;western&quot;&gt;yaffs_readdir_&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;fd&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;()&lt;/code&gt;. Each read will advance the directory read position.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;You can reset to the start of the directory with &lt;code class=&quot;western&quot;&gt;yaffs_rewinddir_&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;fd&lt;/code&gt;&lt;code class=&quot;western&quot;&gt;()&lt;/code&gt;.&lt;/p&gt;
 &lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Close the directory when finished with &lt;code class=&quot;western&quot;&gt;yaffs_close()&lt;/code&gt;.&lt;/p&gt;
 &lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.12 Mount control and similar&lt;/h2&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_mount(path) ; &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_mount2(path, readOnly); &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_unmount(path);&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_unmount2(path, int force); &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_remount(path, force, readOnly);&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_sync(path) ;&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_format(const YCHAR *path, &lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;&lt;/code&gt; &lt;code class=&quot;western&quot;&gt;int unmount_flag, &lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;&lt;/code&gt; &lt;code class=&quot;western&quot;&gt;int force_unmount_flag, &lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;&lt;/code&gt; &lt;code class=&quot;western&quot;&gt;int remount_flag) &lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;A partition must be mounted to be accessed. &lt;code class=&quot;western&quot;&gt;yaffs_mount()&lt;/code&gt; will mount the partition for read/write access. &lt;code class=&quot;western&quot;&gt;yaffs_mount2()&lt;/code&gt; can be used to control whether the access is read/write or read only.&lt;/p&gt;
&lt;p&gt;A partition can be unmounted to remove it from use. &lt;code class=&quot;western&quot;&gt;yaffs_unmount()&lt;/code&gt; will fail if any files are in use whereas &lt;code class=&quot;western&quot;&gt;yaffs_unmount2()&lt;/code&gt; allows you to force the unmount even if files are open. Note that any file handles will then be broken and will no longer access the files.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_remount()&lt;/code&gt; can be used to change the access to a currently mounted partition and is equivalent to making an &lt;code class=&quot;western&quot;&gt;unmount2()&lt;/code&gt; call followed by a &lt;code class=&quot;western&quot;&gt;mount2()&lt;/code&gt; call.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_sync()&lt;/code&gt; does not change the mount status but flushes out any pending data on a partition that is mounted with write access.&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;yaffs_format()&lt;/b&gt;&lt;/span&gt;&lt;/span&gt; provides a mechanism to format a device. It has various parameters.&lt;br /&gt;
&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;unmount_flag&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;: If set, yaffs_format() will unmount the device before formatting. If this flag is not set and the device is mounted, then the format will fail with EBUSY.&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;force_unmount&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;: If set, then an unmount is allowed even if the device is busy (eg. files open). If not set, then yaffs_format() will fail (EBUSY) if files are open.&lt;/p&gt;
&lt;p&gt;&lt;span style=&quot;font-family: Liberation Mono, monospace;&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;b&gt;remount_flag&lt;/b&gt;&lt;/span&gt;&lt;/span&gt;: If set, then the device will be remounted after the format if it was mounted.&lt;/p&gt;
&lt;p&gt;The force_unmount and remount_flag options only have meaning if unmount_flag is set.&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.13 Extended attributes (xattrt)&lt;/h2&gt;
&lt;p&gt;Extended attributes provide a mechanism to attach a limited amount of extra data to a file without actually modifying the file. Each xattribute is a named pair of name and some data. Each file can have as many xattribs as there is space for. In Yaffs, this is around chunk-size – 512 bytes. So on devices with 2kbyte chunks you can store up to 1.5kbytes of xattribute information.&lt;/p&gt;
&lt;p&gt;Although there are 12 xattr functions, there are really only four basic functions, each with 3 different flavours.&lt;/p&gt;
&lt;p&gt;The basic functions are: set an xattr, get an xattr, remove an xattribute and list the xattribute names.&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_setxattr(const char *path, const char *name, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;const void *data, int size, int flags); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_lsetxattr(const char *path, const char *name, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;const void *data, int size, int flags); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_fsetxattr(int fd, const char *name, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;const void *data, int size, int flags); &lt;/p&gt;
&lt;p&gt;These functions are called with name being the name of the xattr, a pointer to the data and the size of the data, and flags.&lt;/p&gt;
&lt;p&gt;The flags are:&lt;/p&gt;
&lt;p&gt;XATTR_CREATE: Create a new xattr, fail with -EEXIST if the xattrib already exists.&lt;/p&gt;
&lt;p&gt;XATTR_REPLACE: Replace an existing xattr, fail with -ENOATTR if it does not exist.&lt;/p&gt;
&lt;p&gt;zero: Just create with no checks, replace if it already exists.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;Setting can fail with -ENOSPC if there is not enough space to store the xattrib.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_getxattr(const char *path, const char *name, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;void *data, int size); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_lgetxattr(const char *path, const char *name, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;void *data, int size); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_fgetxattr(int fd, const char *name, &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;void *data, int size); &lt;/p&gt;
&lt;p&gt;These get (fetch) an xattrib.&lt;/p&gt;
&lt;p&gt;If the call succeeds, the length of the retrieved xattrib is returned. This call can fail with -ENOATTR if the requested xattr does not exist or -ERANGE if the buffer was too small.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_removexattr(const char *path, const char *name); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_lremovexattr(const char *path, const char *name); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_fremovexattr(int fd, const char *name); &lt;/p&gt;
&lt;p&gt;These functions delete an existing xattr. If the xattr does not exist then -ENOATTR is returned.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_listxattr(const char *path, char *list, int size); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_llistxattr(const char *path, char *list, int size); &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;int yaffs_flistxattr(int fd, char *list, int size); &lt;/p&gt;
&lt;p&gt;These functions fetch a list of the xattrib names into the list buffer. The names are NUL terminated. eg. “attrib0\0attrib1\0...”.&lt;/p&gt;
&lt;p&gt;The function returns the length of the list, otherwise if the list buffer is too short it returns -ERANGE.&lt;/p&gt;
&lt;p&gt;Note: If you call these functions with a list buffer size of zero, this acts as a query of the required buffer size. No data is actually transferred into the list.&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;For example we might choose to add some xattribs to a media file:&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;//Set description&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;yaffs_fsetxattr(fd, “user-comment”, “I hate this song!”,18);&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;yaffs_fsetxattr(fd, “price-in-cents”, &amp;amp;cost, sizeof(cost));&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;// Get the comment&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;yaffs_fgetxattr(fd, “user_comment”, buffer, sizeof(buffer);&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;//List the attributes in a NUL delimited list&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;yaffs_flistxattr(fd, list_buf, sizeof(list_buf));&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;// Now list_buf has user-comment\0price-in-cents\0&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;yaffs_fremovexattr(fd, ”user-comment”);&lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;h2 class=&quot;western&quot;&gt;11.14 Other&lt;/h2&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_freespace(path); &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_totalspace(path); &lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;yaffs_inodecount(path); &lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p&gt;These functions provide information on the free and total space (in bytes) for the mount that the path addresses.&lt;/p&gt;
&lt;p&gt;&lt;code class=&quot;western&quot;&gt;yaffs_inodecount()&lt;/code&gt; returns the number of files on the mount that the path addresses.&lt;/p&gt;
&lt;h1 class=&quot;western&quot; style=&quot;page-break-before: always&quot;&gt;12 Example: yaffs_readdir() and yaffs_stat()&lt;/h1&gt;
&lt;p&gt;This code snippet illustrates using &lt;code class=&quot;western&quot;&gt;yaffs_readdir()&lt;/code&gt; and associated functions to iterate through a directory. It also shows how to use &lt;code class=&quot;western&quot;&gt;yaffs_lstat() &lt;/code&gt;to get information on a file and interpret it.&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;void dump_directory(const char *dname) &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;{ &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;yaffs_DIR *d; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;yaffs_dirent *de; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;struct yaffs_stat s; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;char str[100]; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;d = yaffs_opendir(dname); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;if(!d) { &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;printf(&amp;quot;opendir failed\n&amp;quot;); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;} else { &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;while((de = yaffs_readdir(d)) != NULL) { &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;sprintf(str,&amp;quot;%s/%s&amp;quot;,dname,de-&amp;gt;d_name); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;yaffs_lstat(str,&amp;amp;s); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;printf(&amp;quot;%s inode %d length %d mode %X &amp;quot;,&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;str,s.st_ino,(int)s.st_size,s.st_mode); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;switch(s.st_mode &amp;amp; S_IFMT) { &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;case S_IFREG: printf(&amp;quot;data file&amp;quot;); break; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;case S_IFDIR: printf(&amp;quot;directory&amp;quot;); break; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;case S_IFLNK: printf(&amp;quot;symlink --&amp;gt;&amp;quot;); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;if(yaffs_readlink(str,str,100) &amp;lt; 0) &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;printf(&amp;quot;no alias&amp;quot;); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;else &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;printf(&amp;quot;\&amp;quot;%s\&amp;quot;&amp;quot;,str);&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;break; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;default: printf(&amp;quot;unknown&amp;quot;); break; &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;}&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;printf(&amp;quot;\n&amp;quot;); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;if((s.st_mode &amp;amp; S_IFMT) == S_IFDIR)&lt;/span&gt;&lt;/code&gt;&lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;dump_directory_tree_worker(str); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;} &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;&lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;yaffs_closedir(d); &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;} &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p class=&quot;code-western&quot;&gt;&lt;code class=&quot;western&quot;&gt;&lt;span style=&quot;font-size: 10pt; font-size: small; font-size: small;&quot;&gt;} &lt;/span&gt;&lt;/code&gt; &lt;/p&gt;
&lt;p&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;/p&gt;
&lt;/div&gt;
      </description>
  <pubDate>Sun, 22 Jul 2012 23:37:14 +0000</pubDate>
    <dc:creator>Admin</dc:creator>
    <guid isPermaLink="false">453 at https://yaffs.net</guid>
    </item>
<item>
  <title>Yaffs Tuning</title>
  <link>https://yaffs.net/documents/yaffs-tuning</link>
  <description>&lt;span&gt;Yaffs Tuning&lt;/span&gt;
&lt;span&gt;&lt;span lang=&quot;&quot; about=&quot;/user/admin&quot; typeof=&quot;schema:Person&quot; property=&quot;schema:name&quot; datatype=&quot;&quot;&gt;Admin&lt;/span&gt;&lt;/span&gt;
&lt;span&gt;22 July, 2012 - 8:23pm&lt;/span&gt;

      &lt;div class=&quot;field field--name-upload field--type-file field--label-hidden field--items&quot;&gt;
              &lt;div class=&quot;field--item&quot;&gt;&lt;span class=&quot;file file--mime-application-pdf file--application-pdf icon-before&quot;&gt;&lt;span class=&quot;file-icon&quot;&gt;&lt;span class=&quot;icon glyphicon glyphicon-file text-primary&quot; aria-hidden=&quot;true&quot;&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class=&quot;file-link&quot;&gt;&lt;a href=&quot;https://yaffs.net/sites/default/files/downloads/YaffsTuning.pdf&quot; type=&quot;application/pdf; length=93667&quot; title=&quot;Open file in new window&quot; target=&quot;_blank&quot; data-toggle=&quot;tooltip&quot; data-placement=&quot;bottom&quot;&gt;YaffsTuning.pdf&lt;/a&gt;&lt;/span&gt;&lt;span class=&quot;file-size&quot;&gt;91.47 KB&lt;/span&gt;&lt;/span&gt;&lt;/div&gt;
          &lt;/div&gt;
  
            &lt;div class=&quot;field field--name-body field--type-text-with-summary field--label-hidden field--item&quot;&gt;&lt;p&gt; &lt;/p&gt;

&lt;h2&gt;1 Yaffs Direct Configuration&lt;/h2&gt;

&lt;p&gt;Yaffs behaviour is dictated by compile time and run-time flags.&lt;/p&gt;

&lt;h3&gt;1.1 Initialisation Parameters&lt;/h3&gt;

&lt;p&gt;Each yaffs device is configured by a yaffs_DeviceParameterStruct structure which is part of the yaffs_DeviceStruct structure. This contains the following fields:&lt;/p&gt;

&lt;table&gt;&lt;colgroup&gt;&lt;col /&gt;&lt;col /&gt;&lt;/colgroup&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;name&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;An optional name for the device&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;totalBytesPerChunk&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;The number of bytes in the data area of the flash page. If inbandTags is not set then this whole area will be used to store data and the tags will be stored in the spare area. If inbandTags is set then part of this area will be used to store tags and the rest will be used to store data.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;spareBytesPerChunk&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;The number of available bytes in the spare area of the flash page. This excludes space used by ECC, bad block markers etc.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;startBlock&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;The first block in the partition to be used. 0 for first block.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;endBlock&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;The last block in the partition to be used.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;nReservedBlocks&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Number of good blocks blocks reserved for garbage collection etc. Needs to be at least 2, but 5 would be a more typical number.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;inbandTags&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only:Flag indicating whether tags should be stored in the data area. If inbandTags is set then the short Op cache must be enabled (ie nShortOpCaches must be non-zero.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;useNANDECC&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs1 only: Flag indicating whether the driver performs ECC. If this is zero then Yaffs will perform ECC.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;noTagsECC&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: Flag indicating whether the tags have ECC attached to them.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;isYaffs2&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Flag indicating if this is using the Yaffs2 mechanism. If this is not set then Yaffs1 mode of operation is provided.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;nShortOpCaches&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Number of chunks to store in the short operation cache. Zero disables caching. Typical value is 10 to 20 or so. Caching is required for inband tags.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;emptyLostAndFound&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Flag to delete all files in lost and found on mount.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;skipCheckpointRead&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: Flag to skip reading checkpoint on mount. If set then a re-scan is forced.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;skipCheckpointWrite&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: Flag to skip writing checkpoint on sync or unmount.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;refreshPeriod&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: How often Yaffs should do a block refresh. Values less than 10 disable block refreshing. Typical values would be1000.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;initialiseNAND&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Pointer to function to initialise flash driver.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;deinitialiseNAND&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Pointer to function to de-initialise flash driver&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;eraseBlockInNAND&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Pointer to function to erase a flash block&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;writeChunkToNAND&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs1 only: Pointer to function to write a chunk&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;readChunkFromNAND&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs1 only: Pointer to function to read a chunk.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;writeChunkWithTagsToNAND&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: Pointer to function to write a chunk plus tags&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;readChunkWithTagsFromNAND&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: Pointer to function to read a chunk plus tags&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;markNANDBlockBad&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: Function to mark a block bad&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;queryNANDBlock&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs2 only: Function to query a block state&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;gcControl&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Callback function that returns the garbage collector control flags. This is optional.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;removeObjectCallback&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Callback function called when an object is removed. This is set by the wrapper.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;markSuperBlockDirty&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Callback function that is called when a clean file system is first modified. This is set by the wrapper.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;disableSoftDelete&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Yaffs1 only. Debug only. Disables soft deletion if non-zero.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;useHeaderFileSize&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Debug only. Leave as zero&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;disableLazyLoading&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Debug only. Leave as zero.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;wideTnodeDisabled&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Debug only. Leave as zero.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt; &lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;
			&lt;p&gt;deferDirectoryUpdate&lt;/p&gt;
			&lt;/td&gt;
			&lt;td&gt;
			&lt;p&gt;Used to defer directory updates.&lt;/p&gt;
			&lt;/td&gt;
		&lt;/tr&gt;&lt;/table&gt;&lt;p&gt; &lt;/p&gt;

&lt;h3&gt;1.2 Compile-time settings&lt;/h3&gt;

&lt;p&gt;These setting are used to apply compile-time configurations.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_ALWAYS_CHECK_CHUNK_ERASED&lt;/p&gt;

&lt;p&gt;Normally Yaffs checks that chunks are erased only on the first chunk write to each block. This flag allows you to force all chunks to be checked. This is slower, but is worth using when doing early debugging.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_CASE_INSENSITIVE&lt;/p&gt;

&lt;p&gt;When selected case insensitive name comparisons are used. Note that this will not magically change Yaffs to be case insensitive in a case sensitive OS. This needs to be set according to the OS policy. Typically this is only used in Windows CE.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_DIRECT&lt;/p&gt;

&lt;p&gt;Used when compiling Yaffs Direct.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_DISABLE_LAZY_LOAD&lt;/p&gt;

&lt;p&gt;Lazy loading is used to defer loading up object details until the objects are accessed. This makes mount time faster. This flag can disable lazy loading. Debug only.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_ECC_WRONG_ORDER&lt;/p&gt;

&lt;p&gt;This flag should only be used with old Linux MTD code which had a bug in the ECC byte ordering.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_NO_YAFFS1&lt;/p&gt;

&lt;p&gt;Used to say that only Yaffs2 operation should be compiled in. Not currently supported.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_SHORT_NAMES_IN_RAM&lt;/p&gt;

&lt;p&gt;Set to configure Yaffs to store short object names in RAM. This is faster, but uses up more memory.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_UNICODE&lt;/p&gt;

&lt;p&gt;Set to configure Yaffs to use Unicode file names (eg. With WinCE).&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_USE_OWN_SORT&lt;/p&gt;

&lt;p&gt;By default, Yaffs uses qsort for sorting blocks at mount scanning time. This is faster. Using this flag forces Yaffs to use a slow internal sort instead. Debug only.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_UTIL&lt;/p&gt;

&lt;p&gt;Used when compiling Yaffs for utilities.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_WINCE&lt;/p&gt;

&lt;p&gt;Set when compiling Yaffs for WinCE.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFS_YAFFS2&lt;/p&gt;

&lt;p&gt;Set when using Yaffs2 mode. At present this must always be set.&lt;/p&gt;

&lt;p&gt;CONFIG_YAFFSFS_PROVIDE_VALUES&lt;/p&gt;

&lt;p&gt;Used when compiling Yaffs Direct only.&lt;/p&gt;

&lt;h3&gt;2 Tracing mechanism&lt;/h3&gt;

&lt;p&gt;Yaffs has a lot of built in tracing to help debug and integrate. The tracing is controlled by yaffs_traceMask bitmask which allows various sets of tracing to be disabled or enabled at runtime.&lt;/p&gt;

&lt;p&gt;The trace bits are specified in the yaffs_trace.h file.&lt;/p&gt;

&lt;p&gt;The tracing mechanism has also been &#039;hijacked&#039; to provide a control mask for extra verification code when the YAFFS_TRACE_VERIFYxxx trace bits are selected.&lt;/p&gt;

&lt;p&gt;The tracing mechanism is readily integrated into the system via printf-like statements. Tracing is all done through macros which allow the strings to be converted into unicode or similar if need be.&lt;/p&gt;

&lt;h2&gt;3 Linux&lt;/h2&gt;

&lt;h3&gt;3.1 Linux compile-time flags&lt;/h3&gt;

&lt;p&gt;The Linux compile time flags are documented in the Kconfig file and will not be duplicated here.&lt;/p&gt;

&lt;h3&gt;3.2 Linux: /proc/yaffs trace adjustment&lt;/h3&gt;

&lt;p&gt;Under Linux, the tracing mechanism is hooked up to both the /proc/yaffs and the sys interface. The /proc/yaffs interface is very user friendly.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;#cat +os &amp;gt; /proc/yaffs # Enables YAFFS_TRACE_OS&lt;br /&gt;
#cat -all+gc &amp;gt; /proc/yaffs # Disables everything then enable YAFFS_TRACE_GC&lt;br /&gt;
#cat 0xf000 &amp;gt; /proc/yaffs # Set trace mask to specified bitmask.&lt;/code&gt;&lt;/p&gt;

&lt;h3&gt;3.3 Linux: /sys/ interface&lt;/h3&gt;

&lt;p&gt;The Linux /sys/ interface is used by many Linux OS components to access the state of control variables. Some Yaffs variables are available via /sys/module/yaffs2/parameters/ *. Values can be read and modified using standard shell commands or from application programs.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;# ls /sys/module/yaffs2/parameters/ yaffs_auto_checkpoint yaffs_traceMask yaffs_wr_attempts&lt;br /&gt;
# cat /sys/module/yaffs2/parameters/yaffs_auto_checkpoint 1&lt;br /&gt;
# echo &quot;2&quot; &amp;gt; /sys/module/yaffs2/parameters/yaffs_auto_checkpoint&lt;br /&gt;
# cat /sys/module/yaffs2/parameters/yaffs_auto_checkpoint 2 &lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Yaffs currently supports the following variables:&lt;/p&gt;

&lt;p&gt;yaffs_auto_checkpoint: Controls when checkpoints should be written.&lt;/p&gt;

&lt;p&gt;yaffs_traceMask: An alternative, and less user friendly,interface to modify tracing.&lt;/p&gt;

&lt;p&gt;yaffs_wr_attempts: The number of attempts that Yaffs will make to write a chunk.&lt;/p&gt;

&lt;p&gt;yaffs_gc_control: Controls the garbage collector.&lt;/p&gt;

&lt;h3&gt;3.4 Linux: /proc/yaffs state dumping&lt;/h3&gt;

&lt;p&gt;Some of the state of Yaffs mounts can be determined by reading the /proc/yaffs entry.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;# cat /proc/yaffs&lt;br /&gt;
charles@charles-laptop:/opt/y/cvs/yaffs2$ cat /proc/yaffs&lt;br /&gt;
YAFFS built:Mar 16 2010 11:52:25&lt;br /&gt;
$Id: yaffs_fs.c,v 1.101 2010-03-15 22:27:15 charles Exp $&lt;br /&gt;
$Id: yaffs_guts.c,v 1.119 2010-03-12 02:48:34 charles Exp $&lt;br /&gt;&lt;br /&gt;
Device 0 &quot;NAND simulator partition 0&quot; &lt;/code&gt;&lt;br /&gt;&lt;code&gt;startBlock......... 0&lt;br /&gt;
endBlock........... 511&lt;br /&gt;
totalBytesPerChunk. 2048&lt;br /&gt;
useNANDECC......... 1&lt;br /&gt;
noTagsECC.......... 0&lt;br /&gt;
isYaffs2........... 1&lt;br /&gt;
inbandTags......... 0&lt;br /&gt;
emptyLostAndFound.. 1&lt;br /&gt;
disableLazyLoad.... 0&lt;br /&gt;
refreshPeriod...... 10000&lt;br /&gt;
nShortOpCaches..... 10&lt;br /&gt;
nReservedBlocks.... 5&lt;br /&gt;&lt;br /&gt;
nDataBytesPerChunk. 2048&lt;br /&gt;
chunkGroupBits..... 0&lt;br /&gt;
chunkGroupSize..... 1&lt;br /&gt;
nErasedBlocks...... 152&lt;br /&gt;
blocksInCheckpoint. 0&lt;br /&gt;&lt;br /&gt;
nTnodesCreated..... 2300&lt;br /&gt;
nFreeTnodes........ 1852&lt;br /&gt;
nObjectsCreated.... 2300&lt;br /&gt;
nFreeObjects....... 1842&lt;br /&gt;
nFreeChunks........ 27843&lt;br /&gt;&lt;br /&gt;
nPageWrites........ 65993&lt;br /&gt;
nPageReads......... 19631&lt;br /&gt;
nBlockErasures..... 1133&lt;br /&gt;
nGCCopies.......... 37&lt;br /&gt;
garbageCollections. 161&lt;br /&gt;
passiveGCs......... 137&lt;br /&gt;
nRetriedWrites..... 0&lt;br /&gt;
nRetireBlocks...... 0&lt;br /&gt;
eccFixed........... 0&lt;br /&gt;
eccUnfixed......... 0&lt;br /&gt;
tagsEccFixed....... 0&lt;br /&gt;
tagsEccUnfixed..... 0&lt;br /&gt;
cacheHits.......... 44110&lt;br /&gt;
nDeletedFiles...... 0&lt;br /&gt;
nUnlinkedFiles..... 42917&lt;br /&gt;
refreshCount....... 1&lt;br /&gt;
nBackgroudDeletions 0&lt;/code&gt;&lt;/p&gt;

&lt;p&gt; &lt;/p&gt;

&lt;h2&gt;4 Conclusions&lt;/h2&gt;

&lt;p&gt;Yaffs includes many options for changing speed or memory use, with specific flags for the Yaffs Direct Interface as well as Linux. Under Linux many of the control variables can be altered using standard Linux systems.&lt;/p&gt;&lt;/div&gt;
      </description>
  <pubDate>Sun, 22 Jul 2012 19:23:42 +0000</pubDate>
    <dc:creator>Admin</dc:creator>
    <guid isPermaLink="false">451 at https://yaffs.net</guid>
    </item>

  </channel>
</rss>
";}s:9:"#attached";a:2:{s:7:"library";a:2:{i:0;s:18:"views/views.module";i:1;s:16:"core/picturefill";}s:14:"drupalSettings";a:0:{}}s:6:"#cache";a:3:{s:8:"contexts";a:7:{i:0;s:28:"languages:language_interface";i:1;s:5:"theme";i:2;s:8:"timezone";i:3;s:17:"url.path.is_front";i:4;s:8:"url.site";i:5;s:21:"user.node_grants:view";i:6;s:16:"user.permissions";}s:4:"tags";a:27:{i:0;s:31:"config:filter.format.basic_html";i:1;s:30:"config:filter.format.full_html";i:2;s:29:"config:filter.format.raw_html";i:3;s:32:"config:image.style.max_1300x1300";i:4;s:30:"config:image.style.max_325x325";i:5;s:30:"config:image.style.max_650x650";i:6;s:37:"config:responsive_image.styles.narrow";i:7;s:27:"config:views.view.frontpage";i:8;s:7:"file:77";i:9;s:7:"file:80";i:10;s:7:"file:83";i:11;s:7:"file:85";i:12;s:8:"node:347";i:13;s:8:"node:351";i:14;s:8:"node:451";i:15;s:8:"node:453";i:16;s:8:"node:454";i:17;s:8:"node:455";i:18;s:8:"node:466";i:19;s:8:"node:479";i:20;s:8:"node:502";i:21;s:8:"node:503";i:22;s:9:"node_list";i:23;s:9:"node_view";i:24;s:6:"user:1";i:25;s:6:"user:3";i:26;s:6:"user:4";}s:7:"max-age";i:-1;}s:17:"#cache_properties";a:3:{i:0;s:8:"#view_id";i:1;s:30:"#view_display_show_admin_links";i:2;s:23:"#view_display_plugin_id";}}