Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
R
RIOT
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Container Registry
Model registry
Operate
Environments
Monitor
Incidents
Service Desk
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
cm-projects
RIOT
Commits
d5e9994d
Commit
d5e9994d
authored
6 years ago
by
Matthew Blue
Browse files
Options
Downloads
Patches
Plain Diff
sys/eepreg: initial EEPROM registration support
parent
77d97a6f
No related branches found
No related tags found
No related merge requests found
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
sys/eepreg/Makefile
+1
-0
1 addition, 0 deletions
sys/eepreg/Makefile
sys/eepreg/eepreg.c
+498
-0
498 additions, 0 deletions
sys/eepreg/eepreg.c
sys/include/eepreg.h
+271
-0
271 additions, 0 deletions
sys/include/eepreg.h
with
770 additions
and
0 deletions
sys/eepreg/Makefile
0 → 100644
+
1
−
0
View file @
d5e9994d
include
$(RIOTBASE)/Makefile.base
This diff is collapsed.
Click to expand it.
sys/eepreg/eepreg.c
0 → 100644
+
498
−
0
View file @
d5e9994d
/*
* Copyright (C) 2018 Acutam Automation, LLC
*
* This file is subject to the terms and conditions of the GNU Lesser
* General Public License v2.1. See the file LICENSE in the top level
* directory for more details.
*/
/**
* @ingroup sys_eepreg
* @{
*
* @file
* @brief eepreg implementation
*
* @author Matthew Blue <matthew.blue.neuro@gmail.com>
* @}
*/
#include
<errno.h>
#include
<limits.h>
#include
<stdint.h>
#include
<string.h>
#include
"eepreg.h"
#include
"periph/eeprom.h"
#define ENABLE_DEBUG 0
#include
"debug.h"
/* EEPREG magic number */
static
const
char
eepreg_magic
[]
=
"RIOTREG"
;
/* constant lengths */
#define MAGIC_SIZE (sizeof(eepreg_magic) - 1)
/* -1 to remove null */
#define ENT_LEN_SIZ (1U)
/* constant locations */
#define REG_START (EEPROM_RESERV_CPU_LOW + EEPROM_RESERV_BOARD_LOW)
#define REG_MAGIC_LOC (REG_START)
#define REG_END_PTR_LOC (REG_MAGIC_LOC + MAGIC_SIZE)
#define REG_ENT1_LOC (REG_END_PTR_LOC + EEPREG_PTR_LEN)
#define DAT_START (EEPROM_SIZE - EEPROM_RESERV_CPU_HI \
- EEPROM_RESERV_BOARD_HI - 1)
static
inline
uint32_t
_read_meta_uint
(
uint32_t
loc
)
{
uint8_t
data
[
4
];
uint32_t
ret
;
eeprom_read
(
loc
,
data
,
EEPREG_PTR_LEN
);
/* unused array members will be discarded */
ret
=
((
uint32_t
)
data
[
0
]
<<
24
)
|
((
uint32_t
)
data
[
1
]
<<
16
)
|
((
uint32_t
)
data
[
2
]
<<
8
)
|
((
uint32_t
)
data
[
3
]);
/* bit shift to discard unused array members */
ret
>>=
8
*
(
4
-
EEPREG_PTR_LEN
);
return
ret
;
}
static
inline
void
_write_meta_uint
(
uint32_t
loc
,
uint32_t
val
)
{
uint8_t
data
[
4
];
val
<<=
8
*
(
4
-
EEPREG_PTR_LEN
);
data
[
0
]
=
(
uint8_t
)(
val
>>
24
);
data
[
1
]
=
(
uint8_t
)(
val
>>
16
);
data
[
2
]
=
(
uint8_t
)(
val
>>
8
);
data
[
3
]
=
(
uint8_t
)
val
;
eeprom_write
(
loc
,
data
,
EEPREG_PTR_LEN
);
}
static
inline
uint32_t
_get_reg_end
(
void
)
{
return
_read_meta_uint
(
REG_END_PTR_LOC
);
}
static
inline
void
_set_reg_end
(
uint32_t
loc
)
{
_write_meta_uint
(
REG_END_PTR_LOC
,
loc
);
}
static
inline
uint32_t
_get_last_loc
(
uint32_t
reg_end
)
{
if
(
reg_end
==
REG_ENT1_LOC
)
{
/* no entries yet */
return
DAT_START
;
}
return
_read_meta_uint
(
reg_end
-
EEPREG_PTR_LEN
);
}
static
inline
uint32_t
_calc_free_space
(
uint32_t
reg_end
,
uint32_t
last_loc
)
{
return
last_loc
-
reg_end
;
}
static
inline
uint8_t
_get_meta_len
(
uint32_t
meta_loc
)
{
return
eeprom_read_byte
(
meta_loc
);
}
static
inline
void
_set_meta_len
(
uint32_t
meta_loc
,
uint8_t
meta_len
)
{
eeprom_write_byte
(
meta_loc
,
meta_len
);
}
static
inline
uint32_t
_get_data_loc
(
uint32_t
meta_loc
,
uint8_t
meta_len
)
{
/* data location is at the end of meta-data */
return
_read_meta_uint
(
meta_loc
+
meta_len
-
EEPREG_PTR_LEN
);
}
static
inline
void
_set_data_loc
(
uint32_t
meta_loc
,
uint8_t
meta_len
,
uint32_t
data_loc
)
{
/* data location is at the end of meta-data */
_write_meta_uint
(
meta_loc
+
meta_len
-
EEPREG_PTR_LEN
,
data_loc
);
}
static
inline
uint8_t
_calc_name_len
(
uint8_t
meta_len
)
{
/* entry contents: meta-data length, name, data pointer */
return
meta_len
-
ENT_LEN_SIZ
-
EEPREG_PTR_LEN
;
}
static
inline
void
_get_name
(
uint32_t
meta_loc
,
char
*
name
,
uint8_t
meta_len
)
{
/* name is after entry length */
eeprom_read
(
meta_loc
+
ENT_LEN_SIZ
,
(
uint8_t
*
)
name
,
_calc_name_len
(
meta_len
));
}
static
inline
int
_cmp_name
(
uint32_t
meta_loc
,
const
char
*
name
,
uint8_t
meta_len
)
{
/* name is after entry length */
uint32_t
loc
=
meta_loc
+
ENT_LEN_SIZ
;
uint8_t
len
=
_calc_name_len
(
meta_len
);
uint8_t
offset
;
for
(
offset
=
0
;
offset
<
len
;
offset
++
)
{
if
(
name
[
offset
]
==
'\0'
)
{
/* entry name is longer than name */
return
0
;
}
if
(
eeprom_read_byte
(
loc
+
offset
)
!=
(
uint8_t
)
name
[
offset
])
{
/* non-matching character */
return
0
;
}
}
if
(
name
[
offset
]
==
'\0'
)
{
/* entry name is the same length as name */
return
1
;
}
/* entry name is shorter than name */
return
0
;
}
static
inline
uint32_t
_get_meta_loc
(
const
char
*
name
)
{
uint32_t
meta_loc
=
REG_ENT1_LOC
;
uint32_t
reg_end
=
_get_reg_end
();
while
(
meta_loc
<
reg_end
)
{
uint8_t
meta_len
=
_get_meta_len
(
meta_loc
);
if
(
_cmp_name
(
meta_loc
,
name
,
meta_len
))
{
return
meta_loc
;
}
meta_loc
+=
meta_len
;
}
/* no meta-data found */
return
(
uint32_t
)
UINT_MAX
;
}
static
inline
uint32_t
_get_data_len
(
uint32_t
meta_loc
,
uint32_t
data_loc
)
{
uint32_t
prev_loc
;
if
(
meta_loc
==
REG_ENT1_LOC
)
{
prev_loc
=
DAT_START
;
}
else
{
/* previous entry data pointer is just before this entry */
prev_loc
=
_read_meta_uint
(
meta_loc
-
EEPREG_PTR_LEN
);
}
return
prev_loc
-
data_loc
;
}
static
inline
int
_new_entry
(
const
char
*
name
,
uint32_t
data_len
)
{
uint32_t
reg_end
=
_get_reg_end
();
uint32_t
last_loc
=
_get_last_loc
(
reg_end
);
uint32_t
free_space
=
_calc_free_space
(
reg_end
,
last_loc
);
uint8_t
name_len
=
(
uint8_t
)
strlen
(
name
);
uint8_t
meta_len
=
ENT_LEN_SIZ
+
name_len
+
EEPREG_PTR_LEN
;
/* check to see if there is enough room */
if
(
free_space
<
meta_len
+
data_len
)
{
return
-
ENOSPC
;
}
/* set the length of the meta-data */
_set_meta_len
(
reg_end
,
meta_len
);
/* write name of entry */
eeprom_write
(
reg_end
+
ENT_LEN_SIZ
,
(
uint8_t
*
)
name
,
name_len
);
/* set the location of the data */
_set_data_loc
(
reg_end
,
meta_len
,
last_loc
-
data_len
);
/* update end of the registry */
_set_reg_end
(
reg_end
+
meta_len
);
return
0
;
}
static
inline
void
_move_data
(
uint32_t
oldpos
,
uint32_t
newpos
,
uint32_t
len
)
{
for
(
uint32_t
count
=
0
;
count
<
len
;
count
++
)
{
uint32_t
offset
;
if
(
newpos
<
oldpos
)
{
/* move from beginning of data */
offset
=
count
;
}
else
{
/* move from end of data */
offset
=
len
-
count
;
}
uint8_t
byte
=
eeprom_read_byte
(
oldpos
+
offset
);
eeprom_write_byte
(
newpos
+
offset
,
byte
);
}
}
int
eepreg_add
(
uint32_t
*
pos
,
const
char
*
name
,
uint32_t
len
)
{
int
ret
=
eepreg_check
();
if
(
ret
==
-
ENOENT
)
{
/* reg does not exist, so make a new one */
eepreg_reset
();
}
else
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_add] eepreg_check failed
\n
"
);
return
ret
;
}
uint32_t
reg_end
=
_get_reg_end
();
uint32_t
meta_loc
=
_get_meta_loc
(
name
);
if
(
meta_loc
==
(
uint32_t
)
UINT_MAX
)
{
/* entry does not exist, so make a new one */
/* location of the new data */
*
pos
=
_get_last_loc
(
reg_end
)
-
len
;
if
(
_new_entry
(
name
,
len
)
<
0
)
{
DEBUG
(
"[eepreg_add] not enough space for %s
\n
"
,
name
);
return
-
ENOSPC
;
}
return
0
;
}
*
pos
=
_get_data_loc
(
meta_loc
,
_get_meta_len
(
meta_loc
));
if
(
len
!=
_get_data_len
(
meta_loc
,
*
pos
))
{
DEBUG
(
"[eepreg_add] %s already exists with different length
\n
"
,
name
);
return
-
EADDRINUSE
;
}
return
0
;
}
int
eepreg_read
(
uint32_t
*
pos
,
const
char
*
name
)
{
int
ret
=
eepreg_check
();
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_read] eepreg_check failed
\n
"
);
return
ret
;
}
uint32_t
meta_loc
=
_get_meta_loc
(
name
);
if
(
meta_loc
==
(
uint32_t
)
UINT_MAX
)
{
DEBUG
(
"[eepreg_read] no entry for %s
\n
"
,
name
);
return
-
ENOENT
;
}
*
pos
=
_get_data_loc
(
meta_loc
,
_get_meta_len
(
meta_loc
));
return
0
;
}
int
eepreg_write
(
uint32_t
*
pos
,
const
char
*
name
,
uint32_t
len
)
{
uint32_t
reg_end
=
_get_reg_end
();
int
ret
=
eepreg_check
();
if
(
ret
==
-
ENOENT
)
{
/* reg does not exist, so make a new one */
eepreg_reset
();
}
else
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_write] eepreg_check failed
\n
"
);
return
ret
;
}
/* location of the new data */
*
pos
=
_get_last_loc
(
reg_end
)
-
len
;
if
(
_new_entry
(
name
,
len
)
<
0
)
{
DEBUG
(
"[eepreg_write] not enough space for %s
\n
"
,
name
);
return
-
ENOSPC
;
}
return
0
;
}
int
eepreg_rm
(
const
char
*
name
)
{
int
ret
=
eepreg_check
();
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_rm] eepreg_check failed
\n
"
);
return
ret
;
}
uint32_t
meta_loc
=
_get_meta_loc
(
name
);
if
(
meta_loc
==
(
uint32_t
)
UINT_MAX
)
{
DEBUG
(
"[eepreg_rm] no entry for %s
\n
"
,
name
);
return
-
ENOENT
;
}
uint32_t
reg_end
=
_get_reg_end
();
uint32_t
last_loc
=
_get_last_loc
(
reg_end
);
uint8_t
meta_len
=
_get_meta_len
(
meta_loc
);
uint32_t
tot_meta_len
=
reg_end
-
meta_loc
;
uint32_t
data_loc
=
_get_data_loc
(
meta_loc
,
meta_len
);
uint32_t
data_len
=
_get_data_len
(
meta_loc
,
data_loc
);
/* data_loc is above last_loc due to descending order */
uint32_t
tot_data_len
=
data_loc
-
last_loc
;
_move_data
(
meta_loc
+
meta_len
,
meta_loc
,
tot_meta_len
);
_move_data
(
last_loc
,
last_loc
+
data_len
,
tot_data_len
);
reg_end
-=
meta_len
;
_set_reg_end
(
reg_end
);
/* update data locations */
while
(
meta_loc
<
reg_end
)
{
meta_len
=
_get_meta_len
(
meta_loc
);
data_loc
=
_get_data_loc
(
meta_loc
,
meta_len
);
/* addition due to descending order */
_set_data_loc
(
meta_loc
,
meta_len
,
data_loc
+
data_len
);
meta_loc
+=
meta_len
;
}
return
0
;
}
int
eepreg_iter
(
eepreg_iter_cb_t
cb
,
void
*
arg
)
{
uint32_t
reg_end
=
_get_reg_end
();
int
ret
=
eepreg_check
();
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_len] eepreg_check failed
\n
"
);
return
ret
;
}
uint32_t
meta_loc
=
REG_ENT1_LOC
;
while
(
meta_loc
<
reg_end
)
{
uint8_t
meta_len
=
_get_meta_len
(
meta_loc
);
/* size of memory allocation */
uint8_t
name_len
=
_calc_name_len
(
meta_len
);
char
name
[
name_len
+
1
];
/* terminate string */
name
[
name_len
]
=
'\0'
;
_get_name
(
meta_loc
,
name
,
meta_len
);
/* execute callback */
ret
=
cb
(
name
,
arg
);
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_iter] callback reports failure
\n
"
);
return
ret
;
}
/* only advance if cb didn't delete entry */
if
(
_cmp_name
(
meta_loc
,
name
,
meta_len
))
{
meta_loc
+=
meta_len
;
}
}
return
0
;
}
int
eepreg_check
(
void
)
{
char
magic
[
MAGIC_SIZE
];
/* get magic number from EEPROM */
if
(
eeprom_read
(
REG_MAGIC_LOC
,
(
uint8_t
*
)
magic
,
MAGIC_SIZE
)
!=
MAGIC_SIZE
)
{
DEBUG
(
"[eepreg_check] EEPROM read error
\n
"
);
return
-
EIO
;
}
/* check to see if magic number is the same */
if
(
strncmp
(
magic
,
eepreg_magic
,
MAGIC_SIZE
)
!=
0
)
{
DEBUG
(
"[eepreg_check] No registry detected
\n
"
);
return
-
ENOENT
;
}
return
0
;
}
int
eepreg_reset
(
void
)
{
/* write new registry magic number */
if
(
eeprom_write
(
REG_MAGIC_LOC
,
(
uint8_t
*
)
eepreg_magic
,
MAGIC_SIZE
)
!=
MAGIC_SIZE
)
{
DEBUG
(
"[eepreg_reset] EEPROM write error
\n
"
);
return
-
EIO
;
}
/* new registry has no entries */
_set_reg_end
(
REG_ENT1_LOC
);
return
0
;
}
int
eepreg_len
(
uint32_t
*
len
,
const
char
*
name
)
{
int
ret
=
eepreg_check
();
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_len] eepreg_check failed
\n
"
);
return
ret
;
}
uint32_t
meta_loc
=
_get_meta_loc
(
name
);
if
(
meta_loc
==
(
uint32_t
)
UINT_MAX
)
{
DEBUG
(
"[eepreg_len] no entry for %s
\n
"
,
name
);
return
-
ENOENT
;
}
uint32_t
data_loc
=
_get_data_loc
(
meta_loc
,
_get_meta_len
(
meta_loc
));
*
len
=
_get_data_len
(
meta_loc
,
data_loc
);
return
0
;
}
int
eepreg_free
(
uint32_t
*
len
)
{
int
ret
=
eepreg_check
();
if
(
ret
<
0
)
{
DEBUG
(
"[eepreg_free] eepreg_check failed
\n
"
);
return
ret
;
}
uint32_t
reg_end
=
_get_reg_end
();
uint32_t
last_loc
=
_get_last_loc
(
reg_end
);
*
len
=
_calc_free_space
(
reg_end
,
last_loc
);
return
0
;
}
This diff is collapsed.
Click to expand it.
sys/include/eepreg.h
0 → 100644
+
271
−
0
View file @
d5e9994d
/*
* Copyright (C) 2018 Acutam Automation, LLC
*
* This file is subject to the terms and conditions of the GNU Lesser
* General Public License v2.1. See the file LICENSE in the top level
* directory for more details.
*/
/**
* @defgroup sys_eepreg EEPROM registration
* @ingroup sys
* @brief eepreg provides a facility to easily manage the locations of
* data stored in EEPROM via a meta-data registry.
*
* The structure of the meta-data registry is intended to make it easy to
* detect the exact layout of existent data so that automatic tools may be
* written to migrate legacy data to new formats. It also allows the addition
* and removal of new entries dynamically.
*
* @note Names are used as identifiers and must be unique! It is also
* recommended to keep them as short as possible (while still being unique and
* human readable), as many systems have very small amounts of EEPROM.
* Disemvowelment can shorten long names while still retaining readability.
*
* @code {unparsed}
* The layout of the EEPROM used looks like this:
* EEPROM_RESERV_CPU_LOW
* EEPROM_RESERV_BOARD_LOW
* Registry magic number ("RIOTREG")
* Registry end pointer
* Registry entry 1 meta-data length (1 byte)
* Registry entry 1 name (unterminated)
* Registry entry 1 data pointer
* Registry entry 2 meta-data length
* Registry entry 2 name
* Registry entry 2 data pointer
* ... (new registry meta-data may be added in ascending order)
* unused space
* ... (new data locations may be added in descending order)
* Entry 2 data
* Entry 1 data
* EEPROM_RESERV_BOARD_HI
* EEPROM_RESERV_CPU_HI
* @endcode
*
* Pointer length is dependent on the size of the available EEPROM (see
* EEPREG_PTR_LEN below).
*
* @{
*
* @file
* @brief eepreg interface definitions
*
* @author Matthew Blue <matthew.blue.neuro@gmail.com>
*/
#ifndef EEPREG_H
#define EEPREG_H
#include
<stdint.h>
#include
"periph_cpu.h"
#include
"periph_conf.h"
#ifdef __cplusplus
extern
"C"
{
#endif
#ifndef EEPROM_RESERV_CPU_LOW
/**
* @brief EEPROM reserved near beginning for use by CPU and related
*
* Change with care, as it may make existing data difficult to migrate
*/
#define EEPROM_RESERV_CPU_LOW (0U)
#endif
#ifndef EEPROM_RESERV_CPU_HI
/**
* @brief EEPROM reserved near end for use by CPU and related
*
* Change with care, as it may make existing data difficult to migrate
*/
#define EEPROM_RESERV_CPU_HI (0U)
#endif
#ifndef EEPROM_RESERV_BOARD_LOW
/**
* @brief EEPROM reserved near beginning for use by board and related
*
* Change with care, as it may make existing data difficult to migrate
*/
#define EEPROM_RESERV_BOARD_LOW (0U)
#endif
#ifndef EEPROM_RESERV_BOARD_HI
/**
* @brief EEPROM reserved near end for use by board and related
*
* Change with care, as it may make existing data difficult to migrate
*/
#define EEPROM_RESERV_BOARD_HI (0U)
#endif
/**
* @brief Size in bytes of pointer meta-data in EEPROM
*/
#if (EEPROM_SIZE > 0x1000000)
#define EEPREG_PTR_LEN (4U)
#elif (EEPROM_SIZE > 0x10000)
#define EEPREG_PTR_LEN (3U)
#elif (EEPROM_SIZE > 0x100)
#define EEPREG_PTR_LEN (2U)
#else
#define EEPREG_PTR_LEN (1U)
#endif
/**
* @brief Signature of callback for iterating over entries in EEPROM registry
*
* @param[in] name name of an entry in the registry
* @param[in] arg argument for cb
*
* @return 0 on success
* @return < 0 on failure
*/
typedef
int
(
*
eepreg_iter_cb_t
)(
char
*
name
,
void
*
arg
);
/**
* @brief Load or write meta-data in EEPROM registry
*
* This checks to see if relevant meta-data exists in the EEPROM registry, and
* returns that data position if it exists. If an entry does not exist in the
* registry, meta-data is written and allocated data space if there is enough
* remaining. Requesting a different length for an existent entry returns an
* error.
*
* @param[out] pos pointer to position variable
* @param[in] name name of entry to load or write
* @param[in] len requested amount of data storage
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOSPC on insufficient EEPROM for entry
* @return -EADDRINUSE on existing entry with different length
*/
int
eepreg_add
(
uint32_t
*
pos
,
const
char
*
name
,
uint32_t
len
);
/**
* @brief Read position meta-data from EEPROM registry
*
* This is similar to eepreg_add, except it never writes meta-data.
*
* @param[out] pos pointer to position variable
* @param[in] name name of entry to load
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOENT on non-existent registry or entry
*/
int
eepreg_read
(
uint32_t
*
pos
,
const
char
*
name
);
/**
* @brief Write meta-data to EEPROM registry
*
* This ignores existing meta-data and always makes a new entry in the
* registry. Typical use should be through eepreg_add and not eepreg_write.
* If multiple entries with the same name exist, eepreg functions will find
* the oldest. Mainly intended for use by migration utilities.
*
* @param[out] pos pointer to position variable
* @param[in] name name of entry to write
* @param[in] len requested amount of data storage
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOSPC on insufficient EEPROM for entry
*/
int
eepreg_write
(
uint32_t
*
pos
,
const
char
*
name
,
uint32_t
len
);
/**
* @brief Remove entry from EEPROM registry and free space
*
* This removes an entry from the EEPROM registry and its corresponding data
* and moves the data and meta-data of entries after removed entry to occupy
* the freed space. This preserves the structure of the EEPROM registry.
* Warning: this is a read/write intensive operation! Mainly intended for use
* by migration utilities.
*
* @param[in] name name of entry to remove
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOENT on non-existent registry or entry
*/
int
eepreg_rm
(
const
char
*
name
);
/**
* @brief Iterate over meta-data entries in EEPROM registry
*
* This executes a callback over each name in the EEPROM registry. The intended
* work-flow for migration is to: iterate over each entry, check to see if
* migration is needed, duplicate using eepreg_write if needed, migrate data to
* duplicate entry, then delete old entry using eepreg_rm.
*
* @note It is safe for the callback to remove the entry it is called with,
* or to add new entries.
*
* @param[in] cb callback to iterate over entries
* @param[in] arg argument for cb
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOENT on non-existent registry
* @return return value of cb when cb returns < 0
*/
int
eepreg_iter
(
eepreg_iter_cb_t
cb
,
void
*
arg
);
/**
* @brief Check for the presence of meta-data registry
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOENT on non-existent registry
*/
int
eepreg_check
(
void
);
/**
* @brief Clear existing meta-data registry
*
* This removes any existing meta-data registry by writing a new registry with
* no entries.
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
*/
int
eepreg_reset
(
void
);
/**
* @brief Calculate data length from meta-data in EEPROM registry
*
* @note This information is typically already available to code that has
* called eepreg_add.
*
* @param[out] len pointer to length variable
* @param[in] name name of entry to load or write
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOENT on non-existent registry or entry
*/
int
eepreg_len
(
uint32_t
*
len
,
const
char
*
name
);
/**
* @brief Calculate length of remaining EEPROM free space
*
* @param[out] len pointer to length variable
*
* @return 0 on success
* @return -EIO on EEPROM I/O error
* @return -ENOENT on non-existent registry
*/
int
eepreg_free
(
uint32_t
*
len
);
#ifdef __cplusplus
}
#endif
/** @} */
#endif
/* EEPREG_H */
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment