@@ -706,7 +706,7 @@ static void cache_bypass(struct kunit *test)
706706 regmap_exit (map );
707707}
708708
709- static void cache_sync (struct kunit * test )
709+ static void cache_sync_marked_dirty (struct kunit * test )
710710{
711711 const struct regmap_test_param * param = test -> param_value ;
712712 struct regmap * map ;
@@ -743,7 +743,58 @@ static void cache_sync(struct kunit *test)
743743 regmap_exit (map );
744744}
745745
746- static void cache_sync_defaults (struct kunit * test )
746+ static void cache_sync_after_cache_only (struct kunit * test )
747+ {
748+ const struct regmap_test_param * param = test -> param_value ;
749+ struct regmap * map ;
750+ struct regmap_config config ;
751+ struct regmap_ram_data * data ;
752+ unsigned int val [BLOCK_TEST_SIZE ];
753+ unsigned int val_mask ;
754+ int i ;
755+
756+ config = test_regmap_config ;
757+
758+ map = gen_regmap (test , & config , & data );
759+ KUNIT_ASSERT_FALSE (test , IS_ERR (map ));
760+ if (IS_ERR (map ))
761+ return ;
762+
763+ val_mask = GENMASK (config .val_bits - 1 , 0 );
764+ get_random_bytes (& val , sizeof (val ));
765+
766+ /* Put some data into the cache */
767+ KUNIT_EXPECT_EQ (test , 0 , regmap_bulk_write (map , param -> from_reg , val ,
768+ BLOCK_TEST_SIZE ));
769+ for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
770+ data -> written [param -> from_reg + i ] = false;
771+
772+ /* Set cache-only and change the values */
773+ regcache_cache_only (map , true);
774+ for (i = 0 ; i < ARRAY_SIZE (val ); ++ i )
775+ val [i ] = ~val [i ] & val_mask ;
776+
777+ KUNIT_EXPECT_EQ (test , 0 , regmap_bulk_write (map , param -> from_reg , val ,
778+ BLOCK_TEST_SIZE ));
779+ for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
780+ KUNIT_EXPECT_FALSE (test , data -> written [param -> from_reg + i ]);
781+
782+ KUNIT_EXPECT_MEMNEQ (test , & data -> vals [param -> from_reg ], val , sizeof (val ));
783+
784+ /* Exit cache-only and sync the cache without marking hardware registers dirty */
785+ regcache_cache_only (map , false);
786+
787+ KUNIT_EXPECT_EQ (test , 0 , regcache_sync (map ));
788+
789+ /* Did we just write the correct data out? */
790+ KUNIT_EXPECT_MEMEQ (test , & data -> vals [param -> from_reg ], val , sizeof (val ));
791+ for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
792+ KUNIT_EXPECT_TRUE (test , data -> written [param -> from_reg + i ]);
793+
794+ regmap_exit (map );
795+ }
796+
797+ static void cache_sync_defaults_marked_dirty (struct kunit * test )
747798{
748799 const struct regmap_test_param * param = test -> param_value ;
749800 struct regmap * map ;
@@ -775,6 +826,71 @@ static void cache_sync_defaults(struct kunit *test)
775826 for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
776827 KUNIT_EXPECT_EQ (test , i == 2 , data -> written [param -> from_reg + i ]);
777828
829+ /* Rewrite registers back to their defaults */
830+ for (i = 0 ; i < config .num_reg_defaults ; ++ i )
831+ KUNIT_EXPECT_EQ (test , 0 , regmap_write (map , config .reg_defaults [i ].reg ,
832+ config .reg_defaults [i ].def ));
833+
834+ /*
835+ * Resync after regcache_mark_dirty() should not write out registers
836+ * that are at default value
837+ */
838+ for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
839+ data -> written [param -> from_reg + i ] = false;
840+ regcache_mark_dirty (map );
841+ KUNIT_EXPECT_EQ (test , 0 , regcache_sync (map ));
842+ for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
843+ KUNIT_EXPECT_FALSE (test , data -> written [param -> from_reg + i ]);
844+
845+ regmap_exit (map );
846+ }
847+
848+ static void cache_sync_default_after_cache_only (struct kunit * test )
849+ {
850+ const struct regmap_test_param * param = test -> param_value ;
851+ struct regmap * map ;
852+ struct regmap_config config ;
853+ struct regmap_ram_data * data ;
854+ unsigned int orig_val ;
855+ int i ;
856+
857+ config = test_regmap_config ;
858+ config .num_reg_defaults = BLOCK_TEST_SIZE ;
859+
860+ map = gen_regmap (test , & config , & data );
861+ KUNIT_ASSERT_FALSE (test , IS_ERR (map ));
862+ if (IS_ERR (map ))
863+ return ;
864+
865+ KUNIT_EXPECT_EQ (test , 0 , regmap_read (map , param -> from_reg + 2 , & orig_val ));
866+
867+ /* Enter cache-only and change the value of one register */
868+ regcache_cache_only (map , true);
869+ KUNIT_EXPECT_EQ (test , 0 , regmap_write (map , param -> from_reg + 2 , orig_val + 1 ));
870+
871+ /* Exit cache-only and resync, should write out the changed register */
872+ regcache_cache_only (map , false);
873+ for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
874+ data -> written [param -> from_reg + i ] = false;
875+ KUNIT_EXPECT_EQ (test , 0 , regcache_sync (map ));
876+
877+ /* Was the register written out? */
878+ KUNIT_EXPECT_TRUE (test , data -> written [param -> from_reg + 2 ]);
879+ KUNIT_EXPECT_EQ (test , data -> vals [param -> from_reg + 2 ], orig_val + 1 );
880+
881+ /* Enter cache-only and write register back to its default value */
882+ regcache_cache_only (map , true);
883+ KUNIT_EXPECT_EQ (test , 0 , regmap_write (map , param -> from_reg + 2 , orig_val ));
884+
885+ /* Resync should write out the new value */
886+ regcache_cache_only (map , false);
887+ for (i = 0 ; i < BLOCK_TEST_SIZE ; i ++ )
888+ data -> written [param -> from_reg + i ] = false;
889+
890+ KUNIT_EXPECT_EQ (test , 0 , regcache_sync (map ));
891+ KUNIT_EXPECT_TRUE (test , data -> written [param -> from_reg + 2 ]);
892+ KUNIT_EXPECT_EQ (test , data -> vals [param -> from_reg + 2 ], orig_val );
893+
778894 regmap_exit (map );
779895}
780896
@@ -1590,8 +1706,10 @@ static struct kunit_case regmap_test_cases[] = {
15901706 KUNIT_CASE_PARAM (basic_ranges , regcache_types_gen_params ),
15911707 KUNIT_CASE_PARAM (stress_insert , regcache_types_gen_params ),
15921708 KUNIT_CASE_PARAM (cache_bypass , real_cache_types_gen_params ),
1593- KUNIT_CASE_PARAM (cache_sync , real_cache_types_gen_params ),
1594- KUNIT_CASE_PARAM (cache_sync_defaults , real_cache_types_gen_params ),
1709+ KUNIT_CASE_PARAM (cache_sync_marked_dirty , real_cache_types_gen_params ),
1710+ KUNIT_CASE_PARAM (cache_sync_after_cache_only , real_cache_types_gen_params ),
1711+ KUNIT_CASE_PARAM (cache_sync_defaults_marked_dirty , real_cache_types_gen_params ),
1712+ KUNIT_CASE_PARAM (cache_sync_default_after_cache_only , real_cache_types_gen_params ),
15951713 KUNIT_CASE_PARAM (cache_sync_readonly , real_cache_types_gen_params ),
15961714 KUNIT_CASE_PARAM (cache_sync_patch , real_cache_types_gen_params ),
15971715 KUNIT_CASE_PARAM (cache_drop , sparse_cache_types_gen_params ),
0 commit comments