@@ -343,6 +343,20 @@ pub mod guard {
343343 // it can eventually grow to. It cannot be used to determine
344344 // the position of kernel's stack guard.
345345 None
346+ } else if cfg ! ( target_os = "freebsd" ) {
347+ // FreeBSD's stack autogrows, and optionally includes a guard page
348+ // at the bottom. If we try to remap the bottom of the stack
349+ // ourselves, FreeBSD's guard page moves upwards. So we'll just use
350+ // the builtin guard page.
351+ let stackaddr = get_stack_start_aligned ( ) ?;
352+ let guardaddr = stackaddr as usize ;
353+ // Technically the number of guard pages is tunable and controlled
354+ // by the security.bsd.stack_guard_page sysctl, but there are
355+ // few reasons to change it from the default. The default value has
356+ // been 1 ever since FreeBSD 11.1 and 10.4.
357+ const GUARD_PAGES : usize = 1 ;
358+ let guard = guardaddr..guardaddr + GUARD_PAGES * page_size;
359+ Some ( guard)
346360 } else {
347361 // Reallocate the last page of the stack.
348362 // This ensures SIGBUS will be raised on
@@ -371,9 +385,8 @@ pub mod guard {
371385 }
372386
373387 let guardaddr = stackaddr as usize ;
374- let offset = if cfg ! ( target_os = "freebsd" ) { 2 } else { 1 } ;
375388
376- Some ( guardaddr..guardaddr + offset * page_size)
389+ Some ( guardaddr..guardaddr + page_size)
377390 }
378391 }
379392
@@ -417,11 +430,7 @@ pub mod guard {
417430 assert_eq ! ( libc:: pthread_attr_getstack( & attr, & mut stackaddr, & mut size) , 0 ) ;
418431
419432 let stackaddr = stackaddr as usize ;
420- ret = if cfg ! ( target_os = "freebsd" ) {
421- // FIXME does freebsd really fault *below* the guard addr?
422- let guardaddr = stackaddr - guardsize;
423- Some ( guardaddr - PAGE_SIZE . load ( Ordering :: Relaxed ) ..guardaddr)
424- } else if cfg ! ( target_os = "netbsd" ) {
433+ ret = if cfg ! ( any( target_os = "freebsd" , target_os = "netbsd" ) ) {
425434 Some ( stackaddr - guardsize..stackaddr)
426435 } else if cfg ! ( all( target_os = "linux" , target_env = "musl" ) ) {
427436 Some ( stackaddr - guardsize..stackaddr)
0 commit comments