Thread P generic through all

This commit is contained in:
Carl Lerche
2017-08-25 23:45:15 -04:00
parent 88a7d56a60
commit 9bb34d907a
16 changed files with 368 additions and 291 deletions

View File

@@ -8,15 +8,19 @@ use std::marker::PhantomData;
/// Storage for streams
#[derive(Debug)]
pub(super) struct Store<B> {
slab: slab::Slab<Stream<B>>,
pub(super) struct Store<B, P>
where P: Peer,
{
slab: slab::Slab<Stream<B, P>>,
ids: HashMap<StreamId, usize>,
}
/// "Pointer" to an entry in the store
pub(super) struct Ptr<'a, B: 'a> {
pub(super) struct Ptr<'a, B: 'a, P>
where P: Peer + 'a,
{
key: Key,
slab: &'a mut slab::Slab<Stream<B>>,
slab: &'a mut slab::Slab<Stream<B, P>>,
}
/// References an entry in the store.
@@ -24,21 +28,23 @@ pub(super) struct Ptr<'a, B: 'a> {
pub(super) struct Key(usize);
#[derive(Debug)]
pub(super) struct Queue<B, N> {
pub(super) struct Queue<B, N, P>
where P: Peer,
{
indices: Option<store::Indices>,
_p: PhantomData<(B, N)>,
_p: PhantomData<(B, N, P)>,
}
pub(super) trait Next {
fn next<B>(stream: &Stream<B>) -> Option<Key>;
fn next<B, P: Peer>(stream: &Stream<B, P>) -> Option<Key>;
fn set_next<B>(stream: &mut Stream<B>, key: Option<Key>);
fn set_next<B, P: Peer>(stream: &mut Stream<B, P>, key: Option<Key>);
fn take_next<B>(stream: &mut Stream<B>) -> Option<Key>;
fn take_next<B, P: Peer>(stream: &mut Stream<B, P>) -> Option<Key>;
fn is_queued<B>(stream: &Stream<B>) -> bool;
fn is_queued<B, P: Peer>(stream: &Stream<B, P>) -> bool;
fn set_queued<B>(stream: &mut Stream<B>, val: bool);
fn set_queued<B, P: Peer>(stream: &mut Stream<B, P>, val: bool);
}
/// A linked list
@@ -48,27 +54,33 @@ struct Indices {
pub tail: Key,
}
pub(super) enum Entry<'a, B: 'a> {
pub(super) enum Entry<'a, B: 'a, P: Peer + 'a> {
Occupied(OccupiedEntry<'a>),
Vacant(VacantEntry<'a, B>),
Vacant(VacantEntry<'a, B, P>),
}
pub(super) struct OccupiedEntry<'a> {
ids: hash_map::OccupiedEntry<'a, StreamId, usize>,
}
pub(super) struct VacantEntry<'a, B: 'a> {
pub(super) struct VacantEntry<'a, B: 'a, P>
where P: Peer + 'a,
{
ids: hash_map::VacantEntry<'a, StreamId, usize>,
slab: &'a mut slab::Slab<Stream<B>>,
slab: &'a mut slab::Slab<Stream<B, P>>,
}
pub(super) trait Resolve<B> {
fn resolve(&mut self, key: Key) -> Ptr<B>;
pub(super) trait Resolve<B, P>
where P: Peer,
{
fn resolve(&mut self, key: Key) -> Ptr<B, P>;
}
// ===== impl Store =====
impl<B> Store<B> {
impl<B, P> Store<B, P>
where P: Peer,
{
pub fn new() -> Self {
Store {
slab: slab::Slab::new(),
@@ -76,7 +88,7 @@ impl<B> Store<B> {
}
}
pub fn find_mut(&mut self, id: &StreamId) -> Option<Ptr<B>> {
pub fn find_mut(&mut self, id: &StreamId) -> Option<Ptr<B, P>> {
if let Some(&key) = self.ids.get(id) {
Some(Ptr {
key: Key(key),
@@ -87,7 +99,7 @@ impl<B> Store<B> {
}
}
pub fn insert(&mut self, id: StreamId, val: Stream<B>) -> Ptr<B> {
pub fn insert(&mut self, id: StreamId, val: Stream<B, P>) -> Ptr<B, P> {
let key = self.slab.insert(val);
assert!(self.ids.insert(id, key).is_none());
@@ -97,7 +109,7 @@ impl<B> Store<B> {
}
}
pub fn find_entry(&mut self, id: StreamId) -> Entry<B> {
pub fn find_entry(&mut self, id: StreamId) -> Entry<B, P> {
use self::hash_map::Entry::*;
match self.ids.entry(id) {
@@ -116,7 +128,7 @@ impl<B> Store<B> {
}
pub fn for_each<F>(&mut self, mut f: F) -> Result<(), ConnectionError>
where F: FnMut(Ptr<B>) -> Result<(), ConnectionError>,
where F: FnMut(Ptr<B, P>) -> Result<(), ConnectionError>,
{
for &key in self.ids.values() {
f(Ptr {
@@ -129,8 +141,10 @@ impl<B> Store<B> {
}
}
impl<B> Resolve<B> for Store<B> {
fn resolve(&mut self, key: Key) -> Ptr<B> {
impl<B, P> Resolve<B, P> for Store<B, P>
where P: Peer,
{
fn resolve(&mut self, key: Key) -> Ptr<B, P> {
Ptr {
key: key,
slab: &mut self.slab,
@@ -138,15 +152,19 @@ impl<B> Resolve<B> for Store<B> {
}
}
impl<B> ops::Index<Key> for Store<B> {
type Output = Stream<B>;
impl<B, P> ops::Index<Key> for Store<B, P>
where P: Peer,
{
type Output = Stream<B, P>;
fn index(&self, key: Key) -> &Self::Output {
self.slab.index(key.0)
}
}
impl<B> ops::IndexMut<Key> for Store<B> {
impl<B, P> ops::IndexMut<Key> for Store<B, P>
where P: Peer,
{
fn index_mut(&mut self, key: Key) -> &mut Self::Output {
self.slab.index_mut(key.0)
}
@@ -154,8 +172,9 @@ impl<B> ops::IndexMut<Key> for Store<B> {
// ===== impl Queue =====
impl<B, N> Queue<B, N>
impl<B, N, P> Queue<B, N, P>
where N: Next,
P: Peer,
{
pub fn new() -> Self {
Queue {
@@ -178,7 +197,7 @@ impl<B, N> Queue<B, N>
/// Queue the stream.
///
/// If the stream is already contained by the list, return `false`.
pub fn push(&mut self, stream: &mut store::Ptr<B>) -> bool {
pub fn push(&mut self, stream: &mut store::Ptr<B, P>) -> bool {
trace!("Queue::push");
if N::is_queued(stream) {
@@ -215,8 +234,8 @@ impl<B, N> Queue<B, N>
true
}
pub fn pop<'a, R>(&mut self, store: &'a mut R) -> Option<store::Ptr<'a, B>>
where R: Resolve<B>
pub fn pop<'a, R>(&mut self, store: &'a mut R) -> Option<store::Ptr<'a, B, P>>
where R: Resolve<B, P>
{
if let Some(mut idxs) = self.indices {
let mut stream = store.resolve(idxs.head);
@@ -241,14 +260,18 @@ impl<B, N> Queue<B, N>
// ===== impl Ptr =====
impl<'a, B: 'a> Ptr<'a, B> {
impl<'a, B: 'a, P> Ptr<'a, B, P>
where P: Peer,
{
pub fn key(&self) -> Key {
self.key
}
}
impl<'a, B: 'a> Resolve<B> for Ptr<'a, B> {
fn resolve(&mut self, key: Key) -> Ptr<B> {
impl<'a, B: 'a, P> Resolve<B, P> for Ptr<'a, B, P>
where P: Peer,
{
fn resolve(&mut self, key: Key) -> Ptr<B, P> {
Ptr {
key: key,
slab: &mut *self.slab,
@@ -256,16 +279,20 @@ impl<'a, B: 'a> Resolve<B> for Ptr<'a, B> {
}
}
impl<'a, B: 'a> ops::Deref for Ptr<'a, B> {
type Target = Stream<B>;
impl<'a, B: 'a, P> ops::Deref for Ptr<'a, B, P>
where P: Peer,
{
type Target = Stream<B, P>;
fn deref(&self) -> &Stream<B> {
fn deref(&self) -> &Stream<B, P> {
&self.slab[self.key.0]
}
}
impl<'a, B: 'a> ops::DerefMut for Ptr<'a, B> {
fn deref_mut(&mut self) -> &mut Stream<B> {
impl<'a, B: 'a, P> ops::DerefMut for Ptr<'a, B, P>
where P: Peer,
{
fn deref_mut(&mut self) -> &mut Stream<B, P> {
&mut self.slab[self.key.0]
}
}
@@ -280,8 +307,10 @@ impl<'a> OccupiedEntry<'a> {
// ===== impl VacantEntry =====
impl<'a, B> VacantEntry<'a, B> {
pub fn insert(self, value: Stream<B>) -> Key {
impl<'a, B, P> VacantEntry<'a, B, P>
where P: Peer,
{
pub fn insert(self, value: Stream<B, P>) -> Key {
// Insert the value in the slab
let key = self.slab.insert(value);