8 /****************************************************************************/
9 int main( int argc, char **argv )
12 determine_erg_flag = LOWERED,
14 show_error_flag = LOWERED,
15 show_help_flag = LOWERED,
16 show_version_flag = LOWERED;
24 memory_in_megabytes = TEST_DEFAULT_TEST_MEMORY_IN_MEGABYTES;
26 struct util_cmdline_state
29 union util_cmdline_arg_data
33 assert( argv != NULL );
35 util_cmdline_init( &cs );
37 util_cmdline_add_arg( &cs, 'e', UTIL_CMDLINE_ARG_TYPE_FLAG );
38 util_cmdline_add_arg( &cs, 'h', UTIL_CMDLINE_ARG_TYPE_FLAG );
39 util_cmdline_add_arg( &cs, 'i', UTIL_CMDLINE_ARG_TYPE_INTEGER );
40 util_cmdline_add_arg( &cs, 'm', UTIL_CMDLINE_ARG_TYPE_INTEGER );
41 util_cmdline_add_arg( &cs, 'r', UTIL_CMDLINE_ARG_TYPE_FLAG );
42 util_cmdline_add_arg( &cs, 'v', UTIL_CMDLINE_ARG_TYPE_FLAG );
44 rv = util_cmdline_process_args( &cs, argc, argv );
47 show_error_flag = RAISED;
51 util_cmdline_get_arg_data( &cs, 'e', &arg_data );
52 if( arg_data != NULL )
53 determine_erg_flag = RAISED;
55 util_cmdline_get_arg_data( &cs, 'h', &arg_data );
56 if( arg_data != NULL )
57 show_help_flag = RAISED;
59 util_cmdline_get_arg_data( &cs, 'i', &arg_data );
60 if( arg_data != NULL )
62 if( arg_data->integer.integer < 1 )
64 puts( "Number of iterations needs to be 1 or greater." );
68 iterations = (lfds710_pal_uint_t) arg_data->integer.integer;
71 util_cmdline_get_arg_data( &cs, 'm', &arg_data );
72 if( arg_data != NULL )
74 if( arg_data->integer.integer < 32 )
76 puts( "Memory for tests needs to be 32 or greater." );
80 memory_in_megabytes = (lfds710_pal_uint_t) arg_data->integer.integer;
83 util_cmdline_get_arg_data( &cs, 'r', &arg_data );
84 if( arg_data != NULL )
87 util_cmdline_get_arg_data( &cs, 'v', &arg_data );
88 if( arg_data != NULL )
89 show_version_flag = RAISED;
92 util_cmdline_cleanup( &cs );
94 if( argc == 1 or (run_flag == LOWERED and show_version_flag == LOWERED) )
95 show_help_flag = RAISED;
97 if( show_error_flag == RAISED )
99 printf( "\nInvalid arguments. Sorry - it's a simple parser, so no clues.\n"
100 "-h or run with no args to see the help text.\n" );
105 if( determine_erg_flag == RAISED )
107 enum libtest_misc_determine_erg_result
114 struct libshared_memory_state
120 memory = malloc( ONE_MEGABYTE_IN_BYTES );
122 libshared_memory_init( &ms );
124 libshared_memory_add_memory( &ms, memory, ONE_MEGABYTE_IN_BYTES );
126 libtest_misc_determine_erg( &ms, &count_array, &der, &erg_size_in_bytes );
128 if( der == LIBTEST_MISC_DETERMINE_ERG_RESULT_NOT_SUPPORTED )
129 printf( "Determine ERG not supported on the current platform.\n" );
137 printf( " ERG length in bytes : Number successful LL/SC ops\n"
138 " =================================================\n" );
140 for( loop = 0 ; loop < 10 ; loop++ )
141 printf( " %lu bytes : %llu\n", 1UL << (loop+2), (int long long unsigned) count_array[loop] );
150 case LIBTEST_MISC_DETERMINE_ERG_RESULT_SUCCESS:
151 printf( " The smallest ERG size with successful results is %llu bytes, which\n"
152 " is therefore hopefully if all has gone well the ERG size.\n"
154 " In the file 'lfds710_porting_abstraction_layer_processor.h', in all\n"
155 " the sections for ARM, please replace the existing the value of the\n"
156 " #define LFDS710_PAL_ATOMIC_ISOLATION_IN_BYTES to %llu, like so;\n"
158 " #define LFDS710_PAL_ATOMIC_ISOLATION_IN_BYTES %llu\n",
159 (int long long unsigned) erg_size_in_bytes,
160 (int long long unsigned) erg_size_in_bytes,
161 (int long long unsigned) erg_size_in_bytes );
164 case LIBTEST_MISC_DETERMINE_ERG_RESULT_ONE_PHYSICAL_CORE:
165 printf( " This system has only one physical core, and as such this\n"
166 " code cannot determine the ERG.\n" );
169 case LIBTEST_MISC_DETERMINE_ERG_RESULT_ONE_PHYSICAL_CORE_OR_NO_LLSC:
170 printf( " The results are indeterminate. Either this system has only one\n"
171 " physical core, and as such this code cannot determine the ERG, or\n"
172 " the system has no support for LL/SC.\n" );
175 case LIBTEST_MISC_DETERMINE_ERG_RESULT_NO_LLSC:
176 printf( " There appears to be no LL/SC support on the current platform.\n" );
179 case LIBTEST_MISC_DETERMINE_ERG_RESULT_NOT_SUPPORTED:
180 printf( " Determine ERG not supported on the current platform.\n" );
188 " This code is for ARM and works to empirically determine the ERG size,\n"
189 " which is the value which needs to be used for the #define\n"
190 " LFDS710_PAL_ATOMIC_ISOLATION_IN_BYTES in the file\n"
191 " 'lfds710_porting_abstraction_layer_processor.h'.\n"
193 " It is VERY VERY IMPORTANT to set this value because the default on ARM\n"
194 " is the worst-case, which is 2048 bytes, and this makes all the lfds\n"
195 " data structure structs HUGE.\n"
197 " If this value is set too small, then absolutely none of the liblfds data\n"
198 " structures should work *at all*, so getting it wrong should be very obvious.\n"
200 " Each ERG length is tried 1024 times. All ERG sizes which are smaller than the\n"
201 " actual ERG size should have 0 successful ops. All ERG sizes equal to or\n"
202 " greater than the actual ERG size should have 1024, or maybe a few less,\n"
203 " successful ops. A few spurious failures are not unusual, it's the\n"
204 " nature of LL/SC, so it's normal. The correct ERG size then is the smallest\n"
205 " size which has about 1024 successful ops.\n"
207 " This code however can only work if there are at least two physical cores\n"
208 " in the system. It's not enough to have one physical core with multiple\n"
209 " logical cores. If the ERG size of 4 bytes has any successes, then the\n"
210 " current systems has only a single physical processor, or it has no\n"
211 " support for LL/SC (which can happen - there are SO many ARM system\n"
218 if( show_help_flag == RAISED )
220 printf( "test -e -h -i [n] -m [n] -r -v\n"
221 " -e : empirically determine Exclusive Reservation Granule\n"
222 " (currently supports only ARM32)\n"
224 " -i [n] : number of iterations (default : 1)\n"
225 " -m [n] : memory for tests, in mb (default : %u)\n"
226 " -r : run (causes test to run; present so no args gives help)\n"
227 " -v : version\n", (int unsigned) TEST_DEFAULT_TEST_MEMORY_IN_MEGABYTES );
232 if( show_version_flag == RAISED )
234 internal_show_version();
238 if( run_flag == RAISED )
240 struct libshared_memory_state
243 struct libtest_results_state
246 struct libtest_testsuite_state
252 test_memory = malloc( memory_in_megabytes * ONE_MEGABYTE_IN_BYTES );
254 libshared_memory_init( &ms );
256 libshared_memory_add_memory( &ms, test_memory, memory_in_megabytes * ONE_MEGABYTE_IN_BYTES );
258 libtest_testsuite_init( &ts, &ms, callback_test_start, callback_test_finish );
260 for( loop = 0 ; loop < (lfds710_pal_uint_t) iterations ; loop++ )
262 libtest_results_init( &rs );
265 "Test Iteration %02llu\n"
266 "=================\n", (int long long unsigned) (loop+1) );
268 libtest_testsuite_run( &ts, &rs );
270 libtest_results_cleanup( &rs );
273 libtest_testsuite_cleanup( &ts );
275 libshared_memory_cleanup( &ms, NULL );