@@ -172,6 +172,9 @@ static int settings_zms_delete(struct settings_zms *cf, uint32_t name_hash)
172172 return rc ;
173173 }
174174#ifndef CONFIG_SETTINGS_ZMS_NO_LL_DELETE
175+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
176+ cf -> ll_has_changed = true;
177+ #endif
175178 rc = settings_zms_unlink_ll_node (cf , name_hash );
176179 if (rc < 0 ) {
177180 return rc ;
@@ -269,11 +272,24 @@ static int settings_zms_load(struct settings_store *cs, const struct settings_lo
269272 }
270273#endif /* CONFIG_SETTINGS_ZMS_LOAD_SUBTREE_PATH */
271274
275+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
276+ uint32_t ll_cache_index = 0 ;
277+
278+ if (cf -> ll_has_changed ) {
279+ /* reload the linked list in cache */
280+ ret = settings_zms_get_last_hash_ids (cf );
281+ if (ret < 0 ) {
282+ return ret ;
283+ }
284+ }
285+ settings_element = cf -> ll_cache [ll_cache_index ++ ];
286+ #else
272287 ret = zms_read (& cf -> cf_zms , ZMS_LL_HEAD_HASH_ID , & settings_element ,
273288 sizeof (struct settings_hash_linked_list ));
274289 if (ret < 0 ) {
275290 return ret ;
276291 }
292+ #endif /* CONFIG_SETTINGS_ZMS_LL_CACHE */
277293 ll_hash_id = settings_element .next_hash ;
278294
279295 /* If subtree is NULL then we must load all found Settings */
@@ -303,12 +319,19 @@ static int settings_zms_load(struct settings_store *cs, const struct settings_lo
303319 return ret ;
304320 }
305321#endif /* CONFIG_SETTINGS_ZMS_NO_LL_DELETE */
306-
307- ret = zms_read (& cf -> cf_zms , ll_hash_id , & settings_element ,
308- sizeof (struct settings_hash_linked_list ));
309- if (ret < 0 ) {
310- return ret ;
322+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
323+ if (ll_cache_index < cf -> ll_cache_next ) {
324+ settings_element = cf -> ll_cache [ll_cache_index ++ ];
325+ } else {
326+ #endif
327+ ret = zms_read (& cf -> cf_zms , ll_hash_id , & settings_element ,
328+ sizeof (struct settings_hash_linked_list ));
329+ if (ret < 0 ) {
330+ return ret ;
331+ }
332+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
311333 }
334+ #endif
312335 /* update next ll_hash_id */
313336 ll_hash_id = settings_element .next_hash ;
314337 continue ;
@@ -335,12 +358,20 @@ static int settings_zms_load(struct settings_store *cs, const struct settings_lo
335358 break ;
336359 }
337360
338- /* update next ll_hash_id */
339- ret = zms_read (& cf -> cf_zms , ll_hash_id , & settings_element ,
340- sizeof (struct settings_hash_linked_list ));
341- if (ret < 0 ) {
342- return ret ;
361+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
362+ if (ll_cache_index < cf -> ll_cache_next ) {
363+ settings_element = cf -> ll_cache [ll_cache_index ++ ];
364+ } else {
365+ #endif
366+ ret = zms_read (& cf -> cf_zms , ll_hash_id , & settings_element ,
367+ sizeof (struct settings_hash_linked_list ));
368+ if (ret < 0 ) {
369+ return ret ;
370+ }
371+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
343372 }
373+ #endif
374+ /* update next ll_hash_id */
344375 ll_hash_id = settings_element .next_hash ;
345376 }
346377
@@ -501,6 +532,12 @@ static int settings_zms_save(struct settings_store *cs, const char *name, const
501532 if (rc < 0 ) {
502533 return rc ;
503534 }
535+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
536+ if (cf -> ll_cache_next < CONFIG_SETTINGS_ZMS_LL_CACHE_SIZE ) {
537+ cf -> ll_cache [cf -> ll_cache_next ] = settings_element ;
538+ cf -> ll_cache_next = cf -> ll_cache_next + 1 ;
539+ }
540+ #endif
504541 /* Now update the previous linked list element */
505542 settings_element .next_hash = name_hash | 1 ;
506543 settings_element .previous_hash = cf -> second_to_last_hash_id ;
@@ -511,6 +548,12 @@ static int settings_zms_save(struct settings_store *cs, const char *name, const
511548 }
512549 cf -> second_to_last_hash_id = cf -> last_hash_id ;
513550 cf -> last_hash_id = name_hash | 1 ;
551+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
552+ if ((cf -> ll_cache_next < CONFIG_SETTINGS_ZMS_LL_CACHE_SIZE ) &&
553+ (cf -> ll_cache_next > 1 )) {
554+ cf -> ll_cache [cf -> ll_cache_next - 2 ] = settings_element ;
555+ }
556+ #endif
514557 }
515558#ifdef CONFIG_SETTINGS_ZMS_NO_LL_DELETE
516559no_ll_update :
@@ -533,6 +576,10 @@ static int settings_zms_get_last_hash_ids(struct settings_zms *cf)
533576 uint32_t ll_last_hash_id = ZMS_LL_HEAD_HASH_ID ;
534577 int rc = 0 ;
535578
579+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
580+ cf -> ll_cache_next = 0 ;
581+ cf -> ll_has_changed = false;
582+ #endif
536583 cf -> hash_collision_num = 0 ;
537584 do {
538585 rc = zms_read (& cf -> cf_zms , ll_last_hash_id , & settings_element ,
@@ -548,11 +595,23 @@ static int settings_zms_get_last_hash_ids(struct settings_zms *cf)
548595 }
549596 cf -> last_hash_id = ZMS_LL_HEAD_HASH_ID ;
550597 cf -> second_to_last_hash_id = 0 ;
598+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
599+ /* store the LL header in cache */
600+ cf -> ll_cache_next = 0 ;
601+ cf -> ll_cache [cf -> ll_cache_next ] = settings_element ;
602+ cf -> ll_cache_next = cf -> ll_cache_next + 1 ;
603+ #endif
551604 return 0 ;
552605 } else if (rc < 0 ) {
553606 return rc ;
554607 }
555608
609+ #ifdef CONFIG_SETTINGS_ZMS_LL_CACHE
610+ if (cf -> ll_cache_next < CONFIG_SETTINGS_ZMS_LL_CACHE_SIZE ) {
611+ cf -> ll_cache [cf -> ll_cache_next ] = settings_element ;
612+ cf -> ll_cache_next = cf -> ll_cache_next + 1 ;
613+ }
614+ #endif
556615 /* increment hash collision number if necessary */
557616 if (ZMS_COLLISION_NUM (ll_last_hash_id ) > cf -> hash_collision_num ) {
558617 cf -> hash_collision_num = ZMS_COLLISION_NUM (ll_last_hash_id );
0 commit comments