Modelling flash memory: progress and scope - Semantic Scholar

3 downloads 0 Views 171KB Size Report
the block level of granularity, whilst reading and writing (or programming) is ..... occur over the lifetime of a flash memory, and for which special “wear-leveling”.
Modelling flash memory: progress and scope Andrew Butterfield1 , Leo Freitas2 , PaweÃl Gancarski1 , and Jim Woodcock2 1



Trinity College Dublin, [email protected] 2 University of York

Abstract. This paper focusses on the modelling of NAND Flash Memory technology, done as part of the POSIX filestore pilot study. This is the first known work on formal models of NAND Flash Memory. We describe recently published results, the current modelling activities, and sketch out our plans for future research in this area.

1

Introduction

This paper focusses on the modelling of NAND Flash Memory technology, which is the implementation platform of choice for filestores in space-probe missions [JH05]. This modelling is being done as part of the POSIX filestore pilot study, undertaken as part of the “Grand Challenge in Computing” [Hoa03] on Verified Software [Woo06]. Flash memory is seen as ideal for these kinds of missions as it has good physical handling properties, being non-volatile, shock-resistant, with no moving or rotating parts, and capable of operating under a wide range of pressures and temperatures. The NAND Flash Memory variant that is the subject of this work is essentially a serial-access device, but with high transfer bandwidth. As such, it is ideally suited for implementing filestores. There is no work on the formal modelling of NAND flash devices known to the authors, but there has been a considerable body of work done on the technical, usage and reliability aspects of NAND flash devices, as well as a wide range of material published regarding the implementation of file systems on NAND flash memory, most of which utilise some form of log-structuring [jKgL99, Woo01, Man02, LP06]. Of interest to a potential space-borne application are techniques that use NAND flash to implement low-power file caches for mobile devices [MDK94, KM06]. A key feature of these schemes is the need to cope with the accumulation of errors over time, a mechanism which is very well understood [A+ 93, SPUP06]. This paper presents fragments of various Z models of NAND Flash memory, but does not give a complete account of the formalisation. The focus here is just to sketch out the main ideas. ∗

This publication has emanated from research conducted with the financial support of Science Foundation Ireland

2

Recent Work

The first formal model of NAND flash memory [BW07], was based on the recently released specification from the “Open NAND Flash Interface (ONFI)” consortium [H+ 06]. That paper focussed on the structural aspects of the devices, i.e, their internal organisation, and an abstract view of the behaviour of those operations deemed mandatory by the standard. The model presented, using the Z notation [Spi92, WD96], was hand-crafted, and intended for human consumption. Perhaps the key observation from that early model was the need to match very closely the six levels of hierarchy described in the ONFI specification (Byte,Page,Block,LogicalUnit,Target,Device), which may have appeared as excessive for an initial formalisation. Nevertheless, each step of the hierarchy captures a distinct change in how the device is accessed and operated, each effectively marking a boundary of the scope of some behaviour (See Figure 1). So the

Datum data unit, typically a byte Page 1–2k bytes typically, read/write(program) unit Block 512-1k pages, erase unit Logical Unit (LUN) 32–64 blocks, independently operating unit Target 1–4 LUNs, concurrent, but sharing off-chip communication Device 1–4 Targets, each with own off-chip channel Fig. 1. Flash-Memory Structure

host may communicate with several targets simultaneously, but with only one LUN within each target at a time. One LUN can be communicating with the host while another does some internal operations. Erasing memory has to be done at the block level of granularity, whilst reading and writing (or programming) is done at the page level. Pages and Blocks are modelled as array of Datum and Pages, respectively, whilst LUNs, Targets and Devices have extra structure in addition to the arrays of Blocks, LUNs and Targets that they contain. AddrData AddrPage AddrBlock AddrLUN IdTarget

== == == == ==

colAddr → Data pageAddr → AddrData blockAddr → AddrPage lunAddr → LUN targetIds → Target

LUNs need to keep a status register to track operation progress and a pageregister to hold data during a Read or Program operation. Targets need to keep track of which of their sub-LUNs is currently active

We then define the various levels of structure using schemas with the relevant array components: Page = b [ info : AddrData ] Block = b [ pages : AddrPage ] LUN = b [ blocks : AddrBlock ; SR : Status; PR : Page ] Target = b [ luns : AddrLUN ; activeLUN : lunAddr ] We can then describe a top-level device as being a collection of identified targets, plus some data related to those blocks found to be bad at manufacture time, along with the manufacturers guarantee regarding the extent of same: NANDFlashDevice targets : IdTarget; maxBadBlocksShipped : N badBlocks : targetIds ↔ (lunAddr × blockAddr ) # badBlocks ≤ maxBadBlocksShipped Given that initial model, emphasis now switched to mechanising the model using the Z-Eves theorem prover [Saa04], as the main aim of GC6 is build repositories of mechanically verified software. This raised a new set of issues, largely related to the need to adapt the model to a form that was most easily handled by the ZEves theorem prover. This model re-factoring involved a greater use of schemas than was present in the original model. For instance, in the original model, the fact that an address was built from smaller fragments was captured as a large cross-product (here LUNAddr , BlkAddr , PageAddr and ColAddr are numeric types denoting the address fragments): RowAddr == (LUNAddr × BlkAddr ) × PageAddr Address == RowAddr × ColAddr For the mechanised model, it proved far more efficient to use schema conjunction: ColAddr BlockAddr RowAddr Address

= b = b = b = b

[ ca : colAddr ] PageAddr = b [ pa : pageAddr ] [ ba : blockAddr ] LUNAddr = b [ la : lunAddr ] LUNAddr ∧ BlockAddr ∧ PageAddr RowAddr ∧ ColAddr

A paper describing the refactoring of the model is currently in preparation [BFW].

3

Current Modelling

Current work looks at modelling operations, both at an atomic level, and in terms of the low-level sequence of data-transfers that are required at the level of the hardware interface.

3.1

Flash Memory Operations

Adopting the terminology of [H+ 06], we use the term device to refer to the NAND Flash memory under consideration, and the term host to refer to the system in which it is deployed. We also only consider a subset of the operations that are deemed mandatory by the specification, namely Page-Program, BlockErase, Read and Read-Status. We shall first present operation specifications which view the operations as atomic, and then proceed to show how some of these involve a sequence of simpler communication operations between the host and device. Finally we shall discuss how operation interleaving may come about, either as a design decision for efficiency, or even as necessitated by the particular hardware interface in use. Given the hierarchical nature of our model, most of the operations are being defined at the lowest level of applicability, and use is being made of Z’s promotion technique [WD96] in order to lift these descriptions to device level. Status-Read When most operations are initiated, the relevant Target records the LUN so selected in its activeLUN component. These operations take time to complete, so the “Read Status” operation allows the host to poll the Target to see if an operation has finished. The Read Status operation returns the current value of the status register of the LUN that was the subject of the previous operation. Page-Read The Read operation returns the current value of the page indicated by the address supplied, and is specified in a manner very similar to that for status reading. However we note that the activeLUN component of the relevant Target is updated by this operation. Page-Program The page-program operation would appear to be structurally very similar to that of reading, with only the data direction being different, except that we also have to allow in general for failure. This complicates matters because the programming occurs at page-level, but any error indication is recorded in the status register at LUN-level. Block-Erase Block Erasure is very similar conceptually to page programming in some ways, in that we have the “split-level” promotions going on, this time at the Block and LUN levels, with the possibility of failure. However the erased state at the block level is itself best described as a “bulk-promotion” of a pagelevel erase operation: PageErase ∆Page ran info 0 = {erased }

Here, rather than promoting the page-erasure to a single selected component of an enclosing block, we are applying it to every such component (hence the term “bulk”-promotion). PhiBulkBP ∆Block ; Page 0 pages 0 = pages ⊕ {pa : pageAddr • (pa, θPage 0 )} Succesful block erasure is taking page-erasure and applying it to every page: BlockEraseOK = b PageErase ∧ PhiBulkBP 3.2

Hardware Interface Model

We now look at how a NAND Flash device is interfaced to at the hardware level, where access is mediated by a sequence of low-level access operations that transfer a single unit of data between the host and the device. Operations such as Page Program or Read are a choreographed sequence of these lower level operations Hardware Interface Overview The main hardware interface consists of a bidirection data bus, handling a data chunk typically 8 or 16 bits wide, coupled with a number of control pins that identify the direction of dataflow (Write: from host to device; Read: from device to host), and the type of data being written: Command, Address, or Data. We can thereby identify four basic I/O Operations: Command A chunk denoting a command is sent to the device. Address A chunk providing an address fragment is sent to the device. Data-Write A chunk of data is uploaded onto the device Data-Read A chunk of data is downloaded from the device. Addresses are sent in chunk-sized fragments, least-significant first. An important point to keep in mind is that all of these data-chunk movements occur at the Target-level of the devices concerned. So, for example, a Read Status operation involves two low-level operations: a command chunk is sent to the device, and shortly afterwards, the status value is read back. By contrast, a Page Read operation is more complex, involving two or three phases, depending on the precise nature of the hardware interface. The first phase involves sending in the relevant command, followed by enough address chunks to identify the page, and a second command chunk. The last phase involves a series of Data-Reads in which the data is brought out of the device, chunk-by-chunk. What is of interest here is what happens in-between the first and last phases. The device transfers the data so identified from the relevant

page, to the page-register of the enclosing LUN. This transfer phase can take up to three orders of magnitude longer than one of the chunk-transfer operations, and so mechanisms are provided to allow the device signal completion to the host. One mechanism for detecting the end of the transfer-phase is to execute a Read Status operation on the device, where the ready component of the status register supplies the same information as the ready/busy pin mentioned above. This polling can easily be done in software, without requiring any special hardware, and also has the advantage of giving the software control over timing issues. Formalising the Hardware “Chunk” Interface We now see that ONFIlevel operations get broken down into sequences of chunk-level actions, but that these may be interleaved in complex ways to get efficient device operation. A important issue to capture in a formal model is a characterisation of when particular chunk-level sequences are valid. We are going to build up a model of the hardware interface by extending the NANDFlashDevice schema with extra state components to support this level of detail, all of these being aggregated into a NANDFlashControl schema. All of these operations are defined at the Target level, and a standard promotion scheme is then used to raise these to device level. NANDFlash = b NANDFlashDevice ∧ NANDFlashControl NANDFlashControl = b ... Chunks and Addresses A source of some complexity, is the relationship between the various address components, and the data-chunks used to convey them over the hardware interface. A typical device [Mic06] will have 512-2048 bytes per page, plus some “spare” and 32-64 pages per block, and typically 1024-4096 blocks per LUN. By contrast, we may have between 1 and 4 LUNS per target. So, we have 10-12 bits in the column address, 5-6 bits in the page address, 1012 bits in the block address and 1-2 bits in the LUN address, all packed into byte-sized chunks. We need to be able to formalise this mapping, an example of which is shown in Figure 2. A general difficulty here is that the mapping varies from device to device, even if all are ONFI-compliant, so it is hard to generalise this. Control State The command chunks are modelled as an enumerated free type: Cmd ::= Reset | Status | Read | Prog | Erase . . . Certain operations may require two command chunks, typically where an address is required, with the commands bracketing the address part. DoubleCmd == {Read , Prog, Erase}

Addr4

Addr3

Addr2

0

Addr1

Addr0

0

L U N Address

Page Block Address Address

Column Address

Fig. 2. Mapping Address Components to Byte Chunks PutCmdRead PutCmdProg PutCmdErase

| | |

command 0 = Read ∧ confirm 0 = Reset ∧ aptr 0 = 0 command 0 = Prog ∧ confirm 0 = Reset ∧ aptr 0 = 0 command 0 = Erase ∧ confirm 0 = Reset ∧ aptr 0 = 2

Fig. 3. Command Chunk Schema Summary

The Reset command is the default/power-up value for these. Also recorded are the address components and chunks required along with a pointer to track their loading. ControlState AddrChunkMap command , confirm : Cmd address : Address areg : 0 . . 4 → Byte; aptr : 0 . . 5 Addresses are always loaded least significant component first, so aptr indicates where the next address component is to be entered, and indicates no further address chunks are required when it has value 5. Command When a command is received by a target, it stores it, and, depending on the command value, then initialises other data components, such as address registers and pointers. The status command requires no address or confirmation: PutCmdStatus ∆ControlState command 0 = Status ∧ confirm 0 = Reset ∧ aptr 0 = 5 The remaining command schemas are very similar with only the predicate part varying — the schema names and predicates are listed in Figure 3 We can only post a confirmation command once all address chunks are loaded, and the command requires it:

PutCmdComplete ∆ControlStatecmdclose? : Cmd aptr = 5 ∧ command ∈ DoubleCmd ∧ confirm = Reset confirm 0 = cmdclose? ∧ aptr 0 = 5

Address The device accepts address chunks as long as the address pointer indicates a space to be filled: PutAddr ∆ControlState addr ? : Byte aptr < 5 areg 0 = areg ⊕ {aptr 7→ addr ?} aptr 0 = aptr + 1

Data-Write A chunk of data written into the device is put into the page-register of the active LUN, at the location indicated by the current column address, which is then incremented. To model this we need to combine the target and control models, using the address mapping as a link: PutData ∆ControlState; ∆Target data? : Byte confirm ∈ WriteCmd luns 0 (activeLUN ).PR(address.ca) = data? address.ca 0 = address.ca + 1 We also require as a pre-condition that the confirm command component indicates that a write action is appropriate. WriteCmd == {Prog} Data-Read Dually to Data-Write, a chunk of data read from the device is taken from the page-register of the active LUN, at the location indicated by the current column address, which is then incremented. GetData ∆ControlState; ∆Target data! : Byte confirm ∈ ReadCmd data! = luns(activeLUN ).PR(address.ca) address.ca 0 = address.ca + 1

ReadCmd == {Status, Read }

3.3

Modelling Internal Control

The ONFI specification describes finite-state machines (FSMs) for both Targets and LUNs that give operation control flow [H+ 06, §7]. In effect the device behaviour is described at the Target level by ` + 1 communicating FSMs, where ` is the number of LUNs per target. Work is currently underway by an M.Sc student to convert the FSM tables in the ONFI document into a CSP[Hoa85, Ros97] description of same, with a view to being able to use the FDR2 model-checker [GGH+ 05] to verify key properties. The goal is to be able to show that the (CSP model of) FSMs are a refinement of (CSP models of) the hardware interface sequences used for flash operations. Initial results from this work have shown a strong case for tool support, not least to be able to validate the resulting CSP model against the FSM tabular descriptions. To this end, support is being developed for encoding the information using SCXML [B+ 08], and using XSLT [Cla99] to translate into both CSP, and a tabular format that can be used in comparison with the ONFI document [H+ 06, §7].

3.4

Current Modelling Goals

Current modelling effort is focussing on drawing all of these strands together. A number of modelling challenges remain: Status Checks We need to model the effect of setting up an operation, and then repeatedly performing Status Read checks until the operation is complete/ready. An idea here is to model a “progress” operation that does a non-zero, but otherwise non-deterministically sized chunk of the outstanding work, and then either interleave status reads with this, or have the statusread operation invoke such a progress operation as part of its own behaviour. Internal Control Flow We still need to describe how the operations are choreographed internally by the hardware. We shall need to abstract the CSP models of the controller FSMs in some fashion, and this then raises the issue of linking Z and CSP directly, i.e using Circus[CW03] as the modelling language. Linking Atomic and Hardware-Level We need to find appropriate refinements between the atomic-leve (“specification”) and the hardware level (“implementation”). Z-Eves Getting the model and its proof obligations to pass through Z-Eves.

4

The Future

4.1

Specifying a NAND Flash Memory Controller

An existing project, “Unifying Synchronous Systems” (USS)3 explores the theory of so-called “slotted-Circus”, [BSW07], with a view to using it to give a UTP semantics to hardware compilation languages like Handel-C [Cel02]. This project requires a case-study, and it seems an optimal use of research time to find something that contributes to GC6. Handel-C is not an appropriate tool to implement NAND memory devices, but it is an ideal way to describe the implementation of both NAND Flash memory controllers [TP03, Dat06, LLR07, Eur08], and possible hardware support for bad-block handling. Such controllers mediate between the standard random-access memory interface that most CPUs have (e.g. the ARM AMBA bus specification [ARM99]), and the special serialaccess interface used by NAND Flash devices, as described in §3. We suggest using something like AMBA as a basis for modelling the CPU-side protocol, as this is widely used in industry for IP cores for system-on-chip (SoC) design. 4.2

Software, Hardware & Probability

We have been successful in attracting funding from Science Foundation Ireland (SFI) for work relating to the goals and aims of the POSIX pilot project. The project, “Formalising the Interface between Software and Hardware” (FISH, RFP08/CMS1277), seeks to formalise both the connection between hardware and software, in terms of low-level programming constructs (assembler-level), and to explore probabilistic aspects of the hardware behaviour, and how software might cope with these. Of particular concern here is the wear-related failures that occur over the lifetime of a flash memory, and for which special “wear-leveling” algorithms have been developed. The idea is to explore how some of the recently published probabilistic semantic extensions to programming languages could be exploited within the UTP framework in this regard [He07, JS06] Work would take formal models of flash memory algorithms and data-structures as described in an ACM Survey paper by Gal and Toledo [GT05], and seek to refine these down to the hardware interface level, and then to explore the addition of probability to the underlying NAND Flash hardware model. This research proposal seeks to explore the space between the hardware and the algorithms, by establishing a series of formal models at each level, linked by formal refinement steps. As the key concerns and nature of these models changes considerably moving between the hardware world (finite-state machines, clockspeeds, power-consumption, synchronisation, true parallelism) and the software world (data-structures, algorithms, execution complexity, interleaving concurrency), there is a pressing need for a way to link different theoretical paradigms. 3

Funded by Science Foundation Ireland RFP/08/CMSF186

The complexity of these systems also requires the use of tool-support for modelling, hence its importance to GC6. In [JS06], Galois connections are used to capture the notion of refinement between two semantic models (and their corresponding sets of laws). This work is re-visited in [He07], where a Galois connection is used to show how the semantics of a given language can be extended with new features. One of the extensions discussed is probability, and it is worth pointing out that both [He07] and [JS06] discuss a model where any system with a non-zero probability of failure is deemed to be indistinguishable from certain failure (the “possible failure as failure” model). What is of more interest in fault tolerant systems is the interpretation of a small failure probability as success (the “unlikely failure as success” model) [CGW07, MS07], as exemplified by the “almost-certain termination” approach addressed in [HH07] The goal will be to use this case study to take formal modelling and refinement theory (as embodied in UTP) to the point where it can formally describe flash memory (both functional and probabilistic aspects) the intermediate hardware level and the lower software layers, using appropriate Galois links to propagate probabilities up to the software layer, and to ensure the correctness of refinements down to the hardware level.

5

Conclusions

We have given an overview, past, present, and future, or research into formal modelling of flash memory, as a contribution to the POSIX filestore pilot project of GC6. Even though flash memory is the ‘toe’ of this “top-to-toe” project, it in itself is a rich vein of research ideas and challenges, with scope for a large amount of future work.

References [A+ 93] [ARM99] [B+ 08]

[BFW] [BSW07] [BW07]

Seiichi Aritome et al. Reliability issues of flash memory cells (invited paper). Proc. of the IEEE, 81(5):776–788, May 1993. ARM Ltd. AMBATM Specification (Rev 2.0), 1999. Jim Barnett et al. State chart xml (scxml): State machine notation for control abstraction. http://www.w3.org/TR/scxml/, may 2008. W3C Working Draft. Andrew Butterfield, Leo Freitas, and Jim Woodcock. Mechanising a formal model of flash memory. Science of Programming. subject to revision. Andrew Butterfield, Adnan Sherif, and Jim Woodcock. Slotted-circus. In Davies and Gibbons [DG07], pages 75–97. Andrew Butterfield and Jim Woodcock. Formalising flash memory: First steps. In 12th IEEE International Conference on Engineering Complex Computer Systems, 2007, pages 251–260. IEEE Computer Society, 2007.

[Cel02] [CGW07]

Celoxica Ltd. Handel-C Language Reference Manual v3.0, 2002. Robert Colvin, Lars Grunske, and Kirsten Winter. Probabilistic timed behavior trees. In Davies and Gibbons [DG07], pages 156–175. [Cla99] James Clark. Xsl transformations (xslt) version 1.0. http://www.w3.org/TR/xslt, nov 1999. W3C Recommendation. [CW03] A. L. C. Cavalcanti and J. C. P. Woodcock. Predicate Transformers in the Semantics of Circus. IEE Proceedings Software, 150(1):85 – 94, 2003. [Dat06] Datalight Inc. An overview of NAND Flash memory controllers, 2006. reprinted by LinuxDecives.com. [DG07] Jim Davies and Jeremy Gibbons, editors. Integrated Formal Methods, 6th International Conference, IFM 2007, Oxford, UK, July 2-5, 2007, Proceedings, volume 4591 of Lecture Notes in Computer Science. Springer, 2007. [Eur08] Eureka Technology Inc. EP501 NAND Flash Controller, 2008. IP Core. [GGH+ 05] Paul Gardiner, Michael Goldsmith, Jason Hulance, David Jackson, Bill Roscoe, Bryan Scattergood, and Philip Armstrong. Fdr2 user manual. www.fsel.com, 2005. [GT05] Eran Gal and Sivan Toledo. Algorithms and data structures for flash memories. ACM Comput. Surv., 37(2):138–163, 2005. [H+ 06] Hynix Semiconductor et al. Open NAND Flash Interface Specification. Technical Report Revision 1.0, ONFI, www.onfi.org, 28th December 2006. [He07] Jifeng He. Linking semantic models. In Cliff B. Jones, Zhiming Liu, and Jim Woodcock, editors, Theoretical Aspects of Computing—ICTAC 2007, volume 4711 of LNCS, pages 18–33. Springer, sep 2007. [HH07] Stefan Hallerstede and Thai Son Hoang. Qualitative probabilistic modelling in event-b. In Davies and Gibbons [DG07], pages 293–312. [Hoa85] C. A. R. Hoare. Communicating Sequential Processes. Intl. Series in Computer Science. Prentice Hall, 1985. [Hoa03] Tony Hoare. The verifying compiler: A grand challenge for computing research. Journal of the ACM, 50(1):63–69, 2003. Rajeev Joshi and Gerard J. Holzmann. A mini challenge: Build a verifi[JH05] able filesystem. In Proc. Verified Software: Theories, Tools, Experiments (VSTTE), Z¨ urich, 2005. [jKgL99] Han joon Kim and Sang goo Lee. A new flash memory management for flash storage system. In COMPSAC, page 284. IEEE Computer Society, 1999. [JS06] He Jifeng and J. W. Sanders. Unifying probability. In Steve Dunne and Bill Stoddart, editors, Unifying Theories of Programming, First International Symposium, UTP 2006, Walworth Castle, County Durham, UK, February 5-7, 2006, Revised Selected Papers, volume 4010 of LNCS, pages 173–199. Springer, feb 2006. [KM06] Taeho Kgil and Trevor Mudge. Flashcache: a nand flash memory file cache for low power web servers. In CASES ’06: Proceedings of the 2006 international conference on Compilers, architecture and synthesis for embedded systems, pages 103–112, New York, NY, USA, 2006. ACM Press. [LLR07] Lin Chuan-Sheng Lin and Dung Lang-Rong. A NAND flash memory controller for sd/mmc flash memory card. IEEE Trans. Magnetics, 43(2):933– 5, feb 2007. Seung-Ho Lim and Kyu-Ho Park. An efficient NAND flash file system for [LP06] flash memory storage. IEEE Transactions on Computers, 55(7):906–912, July 2006.

[Man02] [MDK94]

[Mic06] [MS07]

[Ros97] [Saa04] [Spi92] [SPUP06]

[TP03] [WD96] [Woo01] [Woo06]

Charles Manning. Introducing YAFFS, the first NAND-specific flash file system. LinuxDevices.com, Sep 2002. B. Marsh, F. Douglis, and P. Krishnan. Flash memory file caching for mobile computers. In Trevor N. Mudge and Bruce D. Shriver, editors, Proceedings of the 27th Annual Hawaii International Conference on System Sciences, Vol. I: Architecture, HICSS’94 (Maui, Hawaii, January 4-7, 1994), volume 1, pages 451–460, Los Alamitos-Washington-Brussels-Tokyo, 1994. IEEE Computer Society Press. Micron Technology Inc. NAND Flash Memory MT29F4G08AAA, MT29F8G08BAA, MT29F8G08DAA, MT29F16G08FAA, 2006. Larissa Meinicke and Graeme Smith. A stepwise development process for reasoning about the reliability of real-time systems. In Davies and Gibbons [DG07], pages 439–458. A. W. Roscoe. The Theory and Practice of Concurrency. international series in computer science. Prentice Hall, 1997. Mark Saaltink. The Z/EVES 2.0 user’s guide, June 30 2004. J. M. Spivey. The Z Notation: A Reference Manual. International Series in Computer Science. Prentice Hall, 2nd edition, 1992. Axel Sikora, Frank-Peter Pesl, Walter Unger, and Uwe Paschen. Technologies and reliability of modern embedded flash cells. Microelectronics Reliability, 46(12):1980–2005, 2006. Arie Tal and Ziv Paz. Examining nand flash alternatives for mobiles. Comms Design, oct 2003. online EE Times community. Jim Woodcock and Jim Davies. Using Z. Intl. Series in Computer Science. Prentice Hall, 1996. David Woodhouse. JFFS: The Journalling Flash File System. Ottawa Linux Symposium 2001, Oct 2001. Jim Woodcock. First steps in the verified software grand challenge. IEEE Computer, 39(10):57–64, 2006.