kernal/pointer.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108
//! Contains assertions for pointers, which are grouped by the [Pointer] trait. See
//! [PointerAssertions] for more details.
use std::fmt::Debug;
use crate::{AssertThat, Failure};
/// A trait blanket-implemented for all raw pointer types - `*const T` and `*mut T` for all `T`. It
/// defines queries used to make assertions defined in [PointerAssertions].
pub trait Pointer : Copy {
/// Indicates whether this pointer is a null pointer ([std::ptr::null] or [std::ptr::null_mut]).
fn is_null(self) -> bool;
}
impl<T: ?Sized> Pointer for *const T {
fn is_null(self) -> bool {
<*const T>::is_null(self)
}
}
impl<T: ?Sized> Pointer for *mut T {
fn is_null(self) -> bool {
<*mut T>::is_null(self)
}
}
/// An extension trait to be used on the output of [assert_that](crate::assert_that) with an
/// argument that implements the [Pointer] trait, i.e. a raw pointer tye (`*const T` or `*mut T` for
/// all `T`).
///
/// Examples:
///
/// ```
/// use kernal::prelude::*;
///
/// use std::ptr;
///
/// assert_that!(ptr::null::<i32>()).is_null();
/// assert_that!(&0 as *const i32).is_not_null();
/// ```
pub trait PointerAssertions {
/// Asserts that the tested pointer is a null pointer.
fn is_null(self) -> Self;
/// Asserts that the tested pointer is not a null pointer.
fn is_not_null(self) -> Self;
}
impl<T: Debug + Pointer> PointerAssertions for AssertThat<T> {
fn is_null(self) -> Self {
if !self.data.is_null() {
Failure::new(&self)
.expected_it("to be null")
.but_it_was_data(&self)
.fail();
}
self
}
fn is_not_null(self) -> Self {
if self.data.is_null() {
Failure::new(&self).expected_it("not to be null").but_it("was").fail();
}
self
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::{assert_fails, assert_that};
use std::ptr;
#[test]
fn is_null_passes_for_null() {
assert_that!(ptr::null::<i32>()).is_null();
}
#[test]
fn is_null_fails_for_non_null_pointer() {
let pointer = &1 as *const i32;
let but_it = format!("was <{:?}>", pointer);
assert_fails!((pointer).is_null(), expected it "to be null" but it but_it);
}
#[test]
fn is_not_null_passes_for_non_null_pointer() {
assert_that!(&mut 1 as *mut i32).is_not_null();
}
#[test]
fn is_not_null_fails_for_null() {
assert_fails!((ptr::null_mut::<i32>()).is_not_null(),
expected it "not to be null"
but it "was");
}
}