mirror of
https://github.com/espressif/esp-idf.git
synced 2024-10-05 20:47:46 -04:00
refactor(nvs): custom allocator for all objects allocated in NVS
This commit is contained in:
parent
4cba3b68e8
commit
1a3c6f0f19
@ -21,6 +21,7 @@
|
||||
#include "esp_partition.h"
|
||||
#include <functional>
|
||||
#include "nvs_handle_simple.hpp"
|
||||
#include "nvs_memory_management.hpp"
|
||||
#include "esp_err.h"
|
||||
|
||||
#ifdef LINUX_TARGET
|
||||
@ -35,7 +36,7 @@
|
||||
static const char* TAG = "nvs";
|
||||
#endif // ! LINUX_TARGET
|
||||
|
||||
class NVSHandleEntry : public intrusive_list_node<NVSHandleEntry> {
|
||||
class NVSHandleEntry : public intrusive_list_node<NVSHandleEntry>, public ExceptionlessAllocatable {
|
||||
public:
|
||||
NVSHandleEntry(nvs::NVSHandleSimple *handle, const char* part_name)
|
||||
: nvs_handle(handle),
|
||||
|
@ -1,16 +1,8 @@
|
||||
// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#ifndef NVS_HANDLE_SIMPLE_HPP_
|
||||
#define NVS_HANDLE_SIMPLE_HPP_
|
||||
|
||||
@ -18,6 +10,7 @@
|
||||
#include "nvs_storage.hpp"
|
||||
#include "nvs_platform.hpp"
|
||||
|
||||
#include "nvs_memory_management.hpp"
|
||||
#include "nvs_handle.hpp"
|
||||
|
||||
namespace nvs {
|
||||
@ -30,7 +23,9 @@ namespace nvs {
|
||||
*
|
||||
* For more details about the general member functions, see nvs_handle.hpp.
|
||||
*/
|
||||
class NVSHandleSimple : public intrusive_list_node<NVSHandleSimple>, public NVSHandle {
|
||||
class NVSHandleSimple : public intrusive_list_node<NVSHandleSimple>,
|
||||
public NVSHandle,
|
||||
public ExceptionlessAllocatable {
|
||||
friend class NVSPartitionManager;
|
||||
public:
|
||||
NVSHandleSimple(bool readOnly, uint8_t nsIndex, Storage *StoragePtr) :
|
||||
|
@ -1,22 +1,15 @@
|
||||
// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#ifndef nvs_item_hash_list_h
|
||||
#define nvs_item_hash_list_h
|
||||
|
||||
#include "nvs.h"
|
||||
#include "nvs_types.hpp"
|
||||
#include "nvs_memory_management.hpp"
|
||||
#include "intrusive_list.h"
|
||||
|
||||
namespace nvs
|
||||
@ -54,7 +47,7 @@ protected:
|
||||
uint32_t mHash : 24;
|
||||
};
|
||||
|
||||
struct HashListBlock : public intrusive_list_node<HashList::HashListBlock> {
|
||||
struct HashListBlock : public intrusive_list_node<HashList::HashListBlock>, public ExceptionlessAllocatable {
|
||||
HashListBlock();
|
||||
|
||||
static const size_t BYTE_SIZE = 128;
|
||||
|
62
components/nvs_flash/src/nvs_memory_management.hpp
Normal file
62
components/nvs_flash/src/nvs_memory_management.hpp
Normal file
@ -0,0 +1,62 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#include <cstdlib>
|
||||
|
||||
#pragma once
|
||||
|
||||
/**
|
||||
* @brief Type that is only usable with new (std::nothrow) to avoid exceptions.
|
||||
*
|
||||
* This struct shall be inherited by all types in NVS that may be allocated dynamically (with new).
|
||||
*
|
||||
* NVS allocates memory at runtime. Because we use C++, we need to avoid the global ``operator new`` from libstdc++,
|
||||
* since it throws exceptions and we compile NVS with ``-fno-exceptions``. We also need to avoid the global
|
||||
* non-throwing version of that operator from libstdc++, since it is merely a wrapper around the original operator
|
||||
* catching all exceptions.
|
||||
*
|
||||
* This struct removes the normal operator new from this and all types inheriting from it. It furthermore provides
|
||||
* a custom version of operator new (..., const std::nothrow_t&) noexcept that will not use C++ exceptions.
|
||||
*
|
||||
* E.g., if you have a type MyType inheriting from ExceptionlessAllocatable, you want to use it as follows:
|
||||
* @code{c++}
|
||||
* MyType : public ExceptionlessAllocatable {
|
||||
* ExceptionlessAllocatable();
|
||||
* ExceptionlessAllocatable(int param);
|
||||
* };
|
||||
* // ...
|
||||
* MyType *m0 = new (std::nothrow) MyType;
|
||||
* MyType *m1 = new (std::nothrow) MyType(47);
|
||||
* // ...
|
||||
* delete m1;
|
||||
* delete m0;
|
||||
* @endcode
|
||||
*/
|
||||
struct ExceptionlessAllocatable {
|
||||
/**
|
||||
* Disallow use of the default new operator, all of NVS is currently tailored to not throw exceptions
|
||||
*/
|
||||
static void *operator new( std::size_t ) = delete;
|
||||
|
||||
/**
|
||||
* Simple implementation with malloc(). No exceptions are thrown if the allocation fails.
|
||||
* To use this operator, your type must inherit from this class and then allocate with:
|
||||
* @code{c}
|
||||
* new (std::nothrow) <YourType>; // default constructor
|
||||
* new (std::nothrow) <YourType>(<constructor parameters>); // non-default constructor
|
||||
* @endcode
|
||||
*/
|
||||
void *operator new (size_t size, const std::nothrow_t&) noexcept {
|
||||
return std::malloc(size);
|
||||
}
|
||||
|
||||
/**
|
||||
* Use \c delete as normal. This operator will be called automatically instead of the global one from libstdc++.
|
||||
*/
|
||||
void operator delete (void *obj) noexcept {
|
||||
free(obj);
|
||||
}
|
||||
};
|
@ -24,13 +24,14 @@
|
||||
#include "compressed_enum_table.hpp"
|
||||
#include "intrusive_list.h"
|
||||
#include "nvs_item_hash_list.hpp"
|
||||
#include "nvs_memory_management.hpp"
|
||||
#include "partition.hpp"
|
||||
|
||||
namespace nvs
|
||||
{
|
||||
|
||||
|
||||
class Page : public intrusive_list_node<Page>
|
||||
class Page : public intrusive_list_node<Page>, public ExceptionlessAllocatable
|
||||
{
|
||||
public:
|
||||
static const uint32_t PSB_INIT = 0x1;
|
||||
|
@ -1,16 +1,8 @@
|
||||
// Copyright 2019 Espressif Systems (Shanghai) PTE LTD
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2019-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#ifndef ESP_PARTITION_HPP_
|
||||
#define ESP_PARTITION_HPP_
|
||||
@ -18,6 +10,7 @@
|
||||
#include "esp_partition.h"
|
||||
#include "intrusive_list.h"
|
||||
#include "partition.hpp"
|
||||
#include "nvs_memory_management.hpp"
|
||||
|
||||
#define ESP_ENCRYPT_BLOCK_SIZE 16
|
||||
|
||||
@ -31,7 +24,7 @@ namespace nvs {
|
||||
* It is implemented as an intrusive_list_node to easily store instances of it. NVSStorage and NVSPage take pointer
|
||||
* references of this class to abstract their partition operations.
|
||||
*/
|
||||
class NVSPartition : public Partition, public intrusive_list_node<NVSPartition> {
|
||||
class NVSPartition : public Partition, public intrusive_list_node<NVSPartition>, public ExceptionlessAllocatable {
|
||||
public:
|
||||
/**
|
||||
* Copy partition_name to mPartitionName and initialize mESPPartition.
|
||||
|
@ -1,27 +1,20 @@
|
||||
// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#ifndef NVS_PARTITION_MANAGER_HPP_
|
||||
#define NVS_PARTITION_MANAGER_HPP_
|
||||
|
||||
#include "nvs_handle_simple.hpp"
|
||||
#include "nvs_storage.hpp"
|
||||
#include "nvs_partition.hpp"
|
||||
#include "nvs_memory_management.hpp"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
namespace nvs {
|
||||
|
||||
class NVSPartitionManager {
|
||||
class NVSPartitionManager : public ExceptionlessAllocatable {
|
||||
public:
|
||||
virtual ~NVSPartitionManager() { }
|
||||
|
||||
|
@ -1,25 +1,19 @@
|
||||
// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#ifndef nvs_storage_hpp
|
||||
#define nvs_storage_hpp
|
||||
|
||||
#include <memory>
|
||||
#include <cstdlib>
|
||||
#include <unordered_map>
|
||||
#include "nvs.hpp"
|
||||
#include "nvs_types.hpp"
|
||||
#include "nvs_page.hpp"
|
||||
#include "nvs_pagemanager.hpp"
|
||||
#include "nvs_memory_management.hpp"
|
||||
#include "partition.hpp"
|
||||
|
||||
//extern void dumpBytes(const uint8_t* data, size_t count);
|
||||
@ -27,14 +21,14 @@
|
||||
namespace nvs
|
||||
{
|
||||
|
||||
class Storage : public intrusive_list_node<Storage>
|
||||
class Storage : public intrusive_list_node<Storage>, public ExceptionlessAllocatable
|
||||
{
|
||||
enum class StorageState : uint32_t {
|
||||
INVALID,
|
||||
ACTIVE,
|
||||
};
|
||||
|
||||
struct NamespaceEntry : public intrusive_list_node<NamespaceEntry> {
|
||||
struct NamespaceEntry : public intrusive_list_node<NamespaceEntry>, public ExceptionlessAllocatable {
|
||||
public:
|
||||
char mName[Item::MAX_KEY_LENGTH + 1];
|
||||
uint8_t mIndex;
|
||||
@ -42,13 +36,13 @@ class Storage : public intrusive_list_node<Storage>
|
||||
|
||||
typedef intrusive_list<NamespaceEntry> TNamespaces;
|
||||
|
||||
struct UsedPageNode: public intrusive_list_node<UsedPageNode> {
|
||||
struct UsedPageNode: public intrusive_list_node<UsedPageNode>, public ExceptionlessAllocatable {
|
||||
public: Page* mPage;
|
||||
};
|
||||
|
||||
typedef intrusive_list<UsedPageNode> TUsedPageList;
|
||||
|
||||
struct BlobIndexNode: public intrusive_list_node<BlobIndexNode> {
|
||||
struct BlobIndexNode: public intrusive_list_node<BlobIndexNode>, public ExceptionlessAllocatable {
|
||||
public:
|
||||
char key[Item::MAX_KEY_LENGTH + 1];
|
||||
uint8_t nsIndex;
|
||||
|
@ -2562,10 +2562,11 @@ static void check_nvs_part_gen_args(SpiFlashEmulator *spi_flash_emulator,
|
||||
esp_part.address = 0;
|
||||
esp_part.size = size * SPI_FLASH_SEC_SIZE;
|
||||
strncpy(esp_part.label, part_name, PART_NAME_MAX_SIZE);
|
||||
shared_ptr<Partition> part;
|
||||
unique_ptr<nvs::Partition> part;
|
||||
|
||||
if (is_encr) {
|
||||
NVSEncryptedPartition *enc_part = new NVSEncryptedPartition(&esp_part);
|
||||
nvs::NVSEncryptedPartition *enc_part = new (std::nothrow) nvs::NVSEncryptedPartition(&esp_part);
|
||||
REQUIRE(enc_part != nullptr);
|
||||
TEST_ESP_OK(enc_part->init(xts_cfg));
|
||||
part.reset(enc_part);
|
||||
} else {
|
||||
@ -2652,10 +2653,11 @@ static void check_nvs_part_gen_args_mfg(SpiFlashEmulator *spi_flash_emulator,
|
||||
esp_part.address = 0;
|
||||
esp_part.size = size * SPI_FLASH_SEC_SIZE;
|
||||
strncpy(esp_part.label, part_name, PART_NAME_MAX_SIZE);
|
||||
shared_ptr<Partition> part;
|
||||
unique_ptr<nvs::Partition> part;
|
||||
|
||||
if (is_encr) {
|
||||
NVSEncryptedPartition *enc_part = new NVSEncryptedPartition(&esp_part);
|
||||
nvs::NVSEncryptedPartition *enc_part = new (std::nothrow) nvs::NVSEncryptedPartition(&esp_part);
|
||||
REQUIRE(enc_part != nullptr);
|
||||
TEST_ESP_OK(enc_part->init(xts_cfg));
|
||||
part.reset(enc_part);
|
||||
} else {
|
||||
|
Loading…
Reference in New Issue
Block a user