blob: b7f83a35690c3cd5579aa1b72d799210ddf4c5dc [file] [log] [blame]
/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
/**
* Copyright (c) 2014-2016, Regents of the University of California,
* Arizona Board of Regents,
* Colorado State University,
* University Pierre & Marie Curie, Sorbonne University,
* Washington University in St. Louis,
* Beijing Institute of Technology,
* The University of Memphis.
*
* This file is part of NFD (Named Data Networking Forwarding Daemon).
* See AUTHORS.md for complete list of NFD authors and contributors.
*
* NFD 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 3 of the License, or (at your option) any later version.
*
* NFD 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
* NFD, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef NFD_DAEMON_TABLE_PIT_ENTRY_HPP
#define NFD_DAEMON_TABLE_PIT_ENTRY_HPP
#include "pit-in-record.hpp"
#include "pit-out-record.hpp"
#include "core/scheduler.hpp"
namespace nfd {
class NameTree;
namespace name_tree {
class Entry;
} // namespace name_tree
class Pit;
namespace pit {
/** \brief represents an unordered collection of InRecords
*/
typedef std::list< InRecord> InRecordCollection;
/** \brief represents an unordered collection of OutRecords
*/
typedef std::list<OutRecord> OutRecordCollection;
/** \brief indicates where duplicate Nonces are found
*/
enum DuplicateNonceWhere {
DUPLICATE_NONCE_NONE = 0,
/// in-record of same face
DUPLICATE_NONCE_IN_SAME = (1 << 0),
/// in-record of other face
DUPLICATE_NONCE_IN_OTHER = (1 << 1),
/// out-record of same face
DUPLICATE_NONCE_OUT_SAME = (1 << 2),
/// out-record of other face
DUPLICATE_NONCE_OUT_OTHER = (1 << 3)
};
/** \brief represents a PIT entry
*/
class Entry : public StrategyInfoHost, noncopyable
{
public:
explicit
Entry(const Interest& interest);
const Interest&
getInterest() const;
/** \return Interest Name
*/
const Name&
getName() const;
/** \brief decides whether Interest can be forwarded to face
*
* \return true if OutRecord of this face does not exist or has expired,
* and there is an InRecord not of this face,
* and scope is not violated
*/
bool
canForwardTo(const Face& face) const;
/** \brief decides whether forwarding Interest to face would violate scope
*
* \return true if scope control would be violated
* \note canForwardTo has more comprehensive checks (including scope control)
* and should be used by most strategies. Outgoing Interest pipeline
* should only check scope because some strategy (eg. vehicular) needs
* to retransmit sooner than OutRecord expiry, or forward Interest
* back to incoming face
*/
bool
violatesScope(const Face& face) const;
/** \brief finds where a duplicate Nonce appears
* \return OR'ed DuplicateNonceWhere
*/
int
findNonce(uint32_t nonce, const Face& face) const;
public: // InRecord
const InRecordCollection&
getInRecords() const;
/** \brief determines whether any InRecord is a local Face
*
* \return true if any InRecord is a local Face,
* false if all InRecords are non-local Faces
*/
bool
hasLocalInRecord() const;
/** \brief inserts a InRecord for face, and updates it with interest
*
* If InRecord for face exists, the existing one is updated.
* This method does not add the Nonce as a seen Nonce.
* \return an iterator to the InRecord
*/
InRecordCollection::iterator
insertOrUpdateInRecord(shared_ptr<Face> face, const Interest& interest);
/** \brief get the InRecord for face
* \return an iterator to the InRecord, or .end if it does not exist
*/
InRecordCollection::const_iterator
getInRecord(const Face& face) const;
/// deletes one InRecord for face if exists
void
deleteInRecord(const Face& face);
/// deletes all InRecords
void
deleteInRecords();
public: // OutRecord
const OutRecordCollection&
getOutRecords() const;
/** \brief inserts a OutRecord for face, and updates it with interest
*
* If OutRecord for face exists, the existing one is updated.
* \return an iterator to the OutRecord
*/
OutRecordCollection::iterator
insertOrUpdateOutRecord(shared_ptr<Face> face, const Interest& interest);
/** \brief get the OutRecord for face
* \return an iterator to the OutRecord, or .end if it does not exist
*/
OutRecordCollection::iterator
getOutRecord(const Face& face);
/// deletes one OutRecord for face if exists
void
deleteOutRecord(const Face& face);
/** \return true if there is one or more unexpired OutRecords
*/
bool
hasUnexpiredOutRecords() const;
public:
scheduler::EventId m_unsatisfyTimer;
scheduler::EventId m_stragglerTimer;
private:
shared_ptr<const Interest> m_interest;
InRecordCollection m_inRecords;
OutRecordCollection m_outRecords;
static const Name LOCALHOST_NAME;
static const Name LOCALHOP_NAME;
shared_ptr<name_tree::Entry> m_nameTreeEntry;
friend class nfd::NameTree;
friend class nfd::name_tree::Entry;
friend class nfd::Pit;
};
inline const Interest&
Entry::getInterest() const
{
return *m_interest;
}
inline const InRecordCollection&
Entry::getInRecords() const
{
return m_inRecords;
}
inline const OutRecordCollection&
Entry::getOutRecords() const
{
return m_outRecords;
}
} // namespace pit
} // namespace nfd
#endif // NFD_DAEMON_TABLE_PIT_ENTRY_HPP