Flash 中的循环缓冲区 [英] Circular Buffer in Flash

查看:46
本文介绍了Flash 中的循环缓冲区的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要将不同长度的项目存储在闪存芯片的循环队列中.每个项目都有它的封装,所以我可以弄清楚它有多大以及下一个项目从哪里开始.当缓冲区中有足够的项目时,它会自动换行.

I need to store items of varying length in a circular queue in a flash chip. Each item will have its encapsulation so I can figure out how big it is and where the next item begins. When there are enough items in the buffer, it will wrap to the beginning.

在闪存芯片中存储循环队列的好方法是什么?

我想存储数以万计的物品的可能性.所以从头开始读取到缓冲区的末尾并不理想,因为搜索到末尾需要时间.

There is a possibility of tens of thousands of items I would like to store. So starting at the beginning and reading to the end of the buffer is not ideal because it will take time to search to the end.

另外,因为它是循环的,我需要能够区分第一个项目和最后一个项目.

Also, because it is circular, I need to be able to distinguish the first item from the last.

最后一个问题是它存储在闪存中,因此擦除每个块既耗时又只能为每个块执行一定次数.

The last problem is that this is stored in flash, so erasing each block is both time consuming and can only be done a set number of times for each block.

推荐答案

一、区块管理:

在每个块的开头放置一个较小的标题.您需要跟踪最旧"和最新"的主要内容是一个块号,它只是以 k 为模递增.k 必须大于您的总块数.理想情况下,使 k 小于您的 MAX 值(例如 0xFFFF),这样您就可以轻松分辨出什么是已擦除块.

Put a smaller header at the start of each block. The main thing you need to keep track of the "oldest" and "newest" is a block number, which simply increments modulo k. k must be greater than your total number of blocks. Ideally, make k less than your MAX value (e.g. 0xFFFF) so you can easily tell what is an erased block.

在启动时,您的代码会依次读取每个块的标头,并在 ni+1 = (ni<的序列中定位第一个和最后一个块/sub> + 1) 模数 k.注意不要被擦除的块(块号例如 0xFFFF)或以某种方式损坏的数据(例如不完全擦除)弄糊涂.

At start-up, your code reads the headers of each block in turn, and locates the first and last blocks in the sequence that is ni+1 = (ni + 1) MODULO k. Take care not to get confused by erased blocks (block number is e.g. 0xFFFF) or data that is somehow corrupted (e.g. incomplete erase).

在每个区块内

每个块最初都是空的(每个字节都是 0xFF).每条记录只是一个接一个地写入.如果您有固定大小的记录,那么您可以使用简单的索引来访问它.如果您有可变大小的记录,那么要读取它,您必须从块的开头进行扫描,链表样式.

Each block initially starts empty (each byte is 0xFF). Each record is simply written one after the other. If you have fixed-size records, then you can access it with a simple index. If you have variable-size records, then to read it you have to scan from the start of the block, linked-list style.

如果您想拥有可变大小的记录,但要避免线性扫描,那么您可以在每条记录上都有一个明确定义的标题.例如.使用 0 作为记录分隔符,并使用 COBS-encode(或 COBS/R-encode) 每条记录.或者使用您选择的字节作为分隔符,如果该字节出现在每条记录中,则转义"该字节(类似于 PPP 协议).

If you want to have variable-size records, but avoid linear scan, then you could have a well defined header on each record. E.g. use 0 as a record delimiter, and COBS-encode (or COBS/R-encode) each record. Or use a byte of your choice as a delimiter, and 'escape' that byte if it occurs in each record (similar to the PPP protocol).

在启动时,一旦你知道你的最新区块,你就可以对最新记录进行线性扫描.或者,如果您有固定大小的记录或记录分隔符,您可以进行二分搜索.

At start-up, once you know your latest block, you can do a linear scan for the latest record. Or if you have fixed-size records or record delimiters, you could do a binary search.

清除计划

对于某些闪存芯片,擦除一个块可能需要很长时间 - 例如.5秒.考虑提前"将擦除安排为后台任务.例如.当当前块已满 x% 时,开始擦除下一个块.

For some Flash memory chips, erasing a block can take significant time--e.g. 5 seconds. Consider scheduling an erase as a background task a bit "ahead of time". E.g. when the current block is x% full, then start erasing the next block.

记录编号

您可能想要对记录进行编号.我过去的做法是在每个块的标题中放置第一条记录的记录号.然后软件必须对块内每条记录的数量进行计数.

You may want to number records. The way I've done it in the past is to put, in the header of each block, the record number of the first record. Then the software has to keep count of the numbers of each record within the block.

校验和或 CRC

如果您想检测损坏的数据(例如,由于意外电源故障导致的不完整写入或擦除),那么您可以将校验和或 CRC 添加到每条记录,也许还可以添加到块头.请注意,块头 CRC 只会覆盖头本身,而不是记录,因为在写入每个新记录时它不能被重写.

If you want to detect corrupted data (e.g. incomplete writes or erases due to unexpected power failure), then you can add a checksum or CRC to each record, and perhaps to the block header. Note the block header CRC would only cover the header itself, not the records, since it could not be re-written when each new record is written.

这篇关于Flash 中的循环缓冲区的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆