/* cxx_linuxlist.h * * Copyright (C) 2015 by Sysmocom s.f.m.c. GmbH * Author: Jacob Erlbeck * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #pragma once extern "C" { #include } template struct LListHead { typedef T entry_t; /* This must match the declaration of struct llist_head */ LListHead *next; LListHead *prev; LListHead() : m_back(0) { INIT_LLIST_HEAD(this); } LListHead(T* entry) : m_back(entry) { next = (LListHead *)LLIST_POISON1; prev = (LListHead *)LLIST_POISON2; } T *entry() {return m_back;} const T *entry() const {return m_back;} llist_head &llist() { return *static_cast(static_cast(this)); } const llist_head &llist() const { return *static_cast(static_cast(this)); } private: T *const m_back; }; /* Define a family of casting functions */ template llist_head &llist(LListHead &l) { return l->llist(); } template const llist_head &llist(const LListHead &l) { return l->llist(); } template llist_head *llptr(LListHead *l) { return &(l->llist()); } template const llist_head *llptr(const LListHead *l) { return &(l->llist()); } /* Define type-safe wrapper for the existing linux_list.h functions */ template inline void llist_add(LListHead *new_, LListHead *head) { llist_add(llptr(new_), llptr(head)); } template inline void llist_add_tail(LListHead *new_, LListHead *head) { llist_add_tail(llptr(new_), llptr(head)); } template inline void llist_del(LListHead *entry) { llist_del(llptr(entry)); } template inline void llist_del_init(LListHead *entry) { llist_del_init(llptr(entry)); } template inline void llist_move(LListHead *list, LListHead *head) { llist_move(llptr(list), llptr(head)); } template inline void llist_move_tail(LListHead *list, LListHead *head) { llist_move_tail(llptr(list), llptr(head)); } template inline int llist_empty(const LListHead *head) { return llist_empty(llptr(head)); } template inline void llist_splice(LListHead *list, LListHead *head) { llist_splice(llptr(list), llptr(head)); } template inline void llist_splice_init(LListHead *list, LListHead *head) { llist_splice_init(llptr(list), llptr(head)); }