@@ -239,9 +239,226 @@ static int memblock_add_checks(void)
239
239
return 0 ;
240
240
}
241
241
242
+ /*
243
+ * A simple test that marks a memory block of a specified base address
244
+ * and size as reserved and to the collection of reserved memory regions
245
+ * (memblock.reserved). It checks if a new entry was created and if region
246
+ * counter and total memory size were correctly updated.
247
+ */
248
+ static int memblock_reserve_simple_check (void )
249
+ {
250
+ struct memblock_region * rgn ;
251
+
252
+ rgn = & memblock .reserved .regions [0 ];
253
+
254
+ struct region r = {
255
+ .base = SZ_2G ,
256
+ .size = SZ_128M
257
+ };
258
+
259
+ reset_memblock ();
260
+ memblock_reserve (r .base , r .size );
261
+
262
+ assert (rgn -> base == r .base );
263
+ assert (rgn -> size == r .size );
264
+
265
+ return 0 ;
266
+ }
267
+
268
+ /*
269
+ * A test that tries to mark two memory blocks that don't overlap as reserved
270
+ * and checks if two entries were correctly added to the collection of reserved
271
+ * memory regions (memblock.reserved) and if this change was reflected in
272
+ * memblock.reserved's total size and region counter.
273
+ */
274
+ static int memblock_reserve_disjoint_check (void )
275
+ {
276
+ struct memblock_region * rgn1 , * rgn2 ;
277
+
278
+ rgn1 = & memblock .reserved .regions [0 ];
279
+ rgn2 = & memblock .reserved .regions [1 ];
280
+
281
+ struct region r1 = {
282
+ .base = SZ_256M ,
283
+ .size = SZ_16M
284
+ };
285
+ struct region r2 = {
286
+ .base = SZ_512M ,
287
+ .size = SZ_512M
288
+ };
289
+
290
+ reset_memblock ();
291
+ memblock_reserve (r1 .base , r1 .size );
292
+ memblock_reserve (r2 .base , r2 .size );
293
+
294
+ assert (rgn1 -> base == r1 .base );
295
+ assert (rgn1 -> size == r1 .size );
296
+
297
+ assert (rgn2 -> base == r2 .base );
298
+ assert (rgn2 -> size == r2 .size );
299
+
300
+ assert (memblock .reserved .cnt == 2 );
301
+ assert (memblock .reserved .total_size == r1 .size + r2 .size );
302
+
303
+ return 0 ;
304
+ }
305
+
306
+ /*
307
+ * A test that tries to mark two memory blocks as reserved, where the
308
+ * second one overlaps with the beginning of the first (that is
309
+ * r1.base < r2.base + r2.size).
310
+ * It checks if two entries are merged into one region that starts at r2.base
311
+ * and has size of two regions minus their intersection. The test also verifies
312
+ * that memblock can still see only one entry and has a correct total size of
313
+ * the reserved memory.
314
+ */
315
+ static int memblock_reserve_overlap_top_check (void )
316
+ {
317
+ struct memblock_region * rgn ;
318
+ phys_addr_t total_size ;
319
+
320
+ rgn = & memblock .reserved .regions [0 ];
321
+
322
+ struct region r1 = {
323
+ .base = SZ_1G ,
324
+ .size = SZ_1G
325
+ };
326
+ struct region r2 = {
327
+ .base = SZ_128M ,
328
+ .size = SZ_1G
329
+ };
330
+
331
+ total_size = (r1 .base - r2 .base ) + r1 .size ;
332
+
333
+ reset_memblock ();
334
+ memblock_reserve (r1 .base , r1 .size );
335
+ memblock_reserve (r2 .base , r2 .size );
336
+
337
+ assert (rgn -> base == r2 .base );
338
+ assert (rgn -> size == total_size );
339
+
340
+ assert (memblock .reserved .cnt == 1 );
341
+ assert (memblock .reserved .total_size == total_size );
342
+
343
+ return 0 ;
344
+ }
345
+
346
+ /*
347
+ * A test that tries to mark two memory blocks as reserved, where the
348
+ * second one overlaps with the end of the first entry (that is
349
+ * r2.base < r1.base + r1.size).
350
+ * It checks if two entries are merged into one region that starts at r1.base
351
+ * and has size of two regions minus their intersection. It verifies that
352
+ * memblock can still see only one entry and has a correct total size of the
353
+ * reserved memory.
354
+ */
355
+ static int memblock_reserve_overlap_bottom_check (void )
356
+ {
357
+ struct memblock_region * rgn ;
358
+ phys_addr_t total_size ;
359
+
360
+ rgn = & memblock .reserved .regions [0 ];
361
+
362
+ struct region r1 = {
363
+ .base = SZ_2K ,
364
+ .size = SZ_128K
365
+ };
366
+ struct region r2 = {
367
+ .base = SZ_128K ,
368
+ .size = SZ_128K
369
+ };
370
+
371
+ total_size = (r2 .base - r1 .base ) + r2 .size ;
372
+
373
+ reset_memblock ();
374
+ memblock_reserve (r1 .base , r1 .size );
375
+ memblock_reserve (r2 .base , r2 .size );
376
+
377
+ assert (rgn -> base == r1 .base );
378
+ assert (rgn -> size == total_size );
379
+
380
+ assert (memblock .reserved .cnt == 1 );
381
+ assert (memblock .reserved .total_size == total_size );
382
+
383
+ return 0 ;
384
+ }
385
+
386
+ /*
387
+ * A test that tries to mark two memory blocks as reserved, where the second
388
+ * one is within the range of the first entry (that is
389
+ * (r1.base < r2.base) && (r2.base + r2.size < r1.base + r1.size)).
390
+ * It checks if two entries are merged into one region that stays the
391
+ * same. The counter and total size of available memory are expected to not be
392
+ * updated.
393
+ */
394
+ static int memblock_reserve_within_check (void )
395
+ {
396
+ struct memblock_region * rgn ;
397
+
398
+ rgn = & memblock .reserved .regions [0 ];
399
+
400
+ struct region r1 = {
401
+ .base = SZ_1M ,
402
+ .size = SZ_8M
403
+ };
404
+ struct region r2 = {
405
+ .base = SZ_2M ,
406
+ .size = SZ_64K
407
+ };
408
+
409
+ reset_memblock ();
410
+ memblock_reserve (r1 .base , r1 .size );
411
+ memblock_reserve (r2 .base , r2 .size );
412
+
413
+ assert (rgn -> base == r1 .base );
414
+ assert (rgn -> size == r1 .size );
415
+
416
+ assert (memblock .reserved .cnt == 1 );
417
+ assert (memblock .reserved .total_size == r1 .size );
418
+
419
+ return 0 ;
420
+ }
421
+
422
+ /*
423
+ * A simple test that tries to reserve the same memory block twice.
424
+ * The region counter and total size of reserved memory are expected to not
425
+ * be updated.
426
+ */
427
+ static int memblock_reserve_twice_check (void )
428
+ {
429
+ struct region r = {
430
+ .base = SZ_16K ,
431
+ .size = SZ_2M
432
+ };
433
+
434
+ reset_memblock ();
435
+
436
+ memblock_reserve (r .base , r .size );
437
+ memblock_reserve (r .base , r .size );
438
+
439
+ assert (memblock .reserved .cnt == 1 );
440
+ assert (memblock .reserved .total_size == r .size );
441
+
442
+ return 0 ;
443
+ }
444
+
445
+ static int memblock_reserve_checks (void )
446
+ {
447
+ memblock_reserve_simple_check ();
448
+ memblock_reserve_disjoint_check ();
449
+ memblock_reserve_overlap_top_check ();
450
+ memblock_reserve_overlap_bottom_check ();
451
+ memblock_reserve_within_check ();
452
+ memblock_reserve_twice_check ();
453
+
454
+ return 0 ;
455
+ }
456
+
242
457
int memblock_basic_checks (void )
243
458
{
244
459
memblock_initialization_check ();
245
460
memblock_add_checks ();
461
+ memblock_reserve_checks ();
462
+
246
463
return 0 ;
247
464
}
0 commit comments