diff --git a/ndn.cxx/ndn-api-face.cc b/ndn.cxx/ndn-api-face.cc
index 6b80251..4c7cc10 100644
--- a/ndn.cxx/ndn-api-face.cc
+++ b/ndn.cxx/ndn-api-face.cc
@@ -16,198 +16,202 @@
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  *
  * Author: Alexander Afanasyev <alexander.afanasyev@ucla.edu>
- *         Zhenkai Zhu <zhenkai@cs.ucla.edu>
- *         Chaoyi Bian <bcy@pku.edu.cn>
  */
 
 #include "ndn-api-face.h"
+#include "detail/filter-entry.h"
 
-#include <boost/throw_exception.hpp>
-#include <boost/date_time/posix_time/posix_time.hpp>
-#include <boost/lambda/lambda.hpp>
-#include <boost/lambda/bind.hpp>
-namespace ll = boost::lambda;
+#include <ns3/random-variable.h>
 
-#include <ns3/packet.h>
-
+#include <ns3/ndn-l3-protocol.h>
 #include <ns3/ndn-interest.h>
 #include <ns3/ndn-content-object.h>
 #include <ns3/ndn-face.h>
 #include <ns3/ndn-fib.h>
-#include <ns3/log.h>
 
-typedef boost::error_info<struct tag_errmsg, std::string> errmsg_info_str;
-typedef boost::error_info<struct tag_errmsg, int> errmsg_info_int;
+#include <ns3/packet.h>
+#include <ns3/log.h>
 
 using namespace std;
 using namespace boost;
 using namespace ns3;
 
-#define INIT_LOGGER NS_LOG_COMPONENT_DEFINE
-#define _LOG_DEBUG NS_LOG_DEBUG
-#define _LOG_TRACE NS_LOG_TRACE
-#define _LOG_INFO NS_LOG_INFO
-
-
-INIT_LOGGER ("ndn.ApiFace");
+NS_LOG_COMPONENT_DEFINE ("ndn.ApiFace");
 
 namespace ns3 {
 namespace ndn {
 
-// ApiFace::ApiFace()
-//   : m_rand (0, std::numeric_limits<uint32_t>::max ())
-// {
-// }
-
-// ApiFace::~ApiFace()
-// {
-// }
-
-// int
-// ApiFace::publishRawData (const std::string &name, const char *buf, size_t len, int freshness)
-// {
-//   // NS_LOG_INFO ("Requesting Interest: \n" << interestHeader);
-//   _LOG_INFO (">> publishRawData " << name);
-
-//   static ndn::ContentObjectTail trailer;
+class ApiFacePriv
+{
+public:
+  ApiFacePriv ()
+    : m_rand (0, std::numeric_limits<uint32_t>::max ())
+  {
+  }
   
-//   ndn::ContentObject data;
-//   data.SetName (name);
-//   data.SetFreshness (Seconds (freshness));
+  ns3::UniformVariable m_rand; // nonce generator
 
-//   Ptr<Packet> packet = Create<Packet> (reinterpret_cast<const uint8_t*> (buf), len);
-//   // packet->AddPacketTag (CreateObject<TypeTag> (TypeTag::DATA));
-//   packet->AddHeader (data);
-//   packet->AddTrailer (trailer);
-
-//   m_protocolHandler (packet);
-
-//   m_transmittedContentObjects (&data, packet, this, m_face);
-
-//   return 0;
-// }
+  FilterEntryContainer<ApiFace::DataCallback, Interest> m_pendingInterests;
+  FilterEntryContainer<ApiFace::InterestCallback, Name> m_expectedInterests;
+};
 
 
-// void
-// RawDataCallback2StringDataCallback (ApiFace::StringDataCallback callback, std::string str, const char *buf, size_t len)
-// {
-//   callback (str, string (buf, len));
-// }
+ApiFace::ApiFace (Ptr<Node> node)
+  : Face (node)
+  , m_this (new ApiFacePriv ())
+{
+  NS_ASSERT_MSG (GetNode ()->GetObject<L3Protocol> () != 0,
+                 "NDN stack should be installed on the node " << GetNode ());
 
-// int
-// ApiFace::sendInterestForString (const std::string &strInterest, const StringDataCallback &strDataCallback/*, int retry*/)
-// {
-//   return sendInterest (strInterest, boost::bind (RawDataCallback2StringDataCallback, strDataCallback, _1, _2, _3));
-// }
+  GetNode ()->GetObject<L3Protocol> ()->AddFace (this);
+  this->SetUp (true);
+  this->SetFlags (APPLICATION);
+}
 
-// int ApiFace::sendInterest (const string &strInterest, const RawDataCallback &rawDataCallback)
-// {
-//   // NS_LOG_INFO ("Requesting Interest: \n" << interestHeader);
-//   _LOG_INFO (">> I " << strInterest);
-//   Ptr<ndn::Name> name = Create<ndn::Name> (strInterest);
+ApiFace::~ApiFace ()
+{
+  delete m_this;
+}
 
-//   ndn::Interest interestHeader;
-//   interestHeader.SetNonce            (m_rand.GetValue ());
-//   interestHeader.SetName             (*name);
-//   interestHeader.SetInterestLifetime (Seconds (9.9)); // really long-lived interests
+void
+ApiFace::ExpressInterest (Ptr<Interest> interest,
+                          DataCallback onData,
+                          TimeoutCallback onTimeout/* = MakeNullCallback< void, Ptr<Interest> > ()*/)
+{
+  NS_LOG_INFO (">> I " << interest->GetName ());
 
-//   Ptr<Packet> packet = Create<Packet> ();
-//   // packet->AddPacketTag (CreateObject<TypeTag> (TypeTag::INTEREST));
-//   packet->AddHeader (interestHeader);
-
-//   // NS_LOG_DEBUG (interestHeader);
+  if (interest->GetNonce () == 0)
+    {
+      interest->SetNonce (m_this->m_rand.GetValue ());
+    }
   
-//   // Record the callback
-//   FilterEntryContainer<RawDataCallback>::iterator entry = m_dataCallbacks.find_exact (*name);
-//   if (entry == m_dataCallbacks.end ())
-//     {
-//       pair<FilterEntryContainer<RawDataCallback>::iterator, bool> status =
-//         m_dataCallbacks.insert (*name, Create< FilterEntry<RawDataCallback> > (name));
+  // Record the callback
+  FilterEntryContainer<DataCallback, Interest>::iterator entry =
+    m_this->m_pendingInterests.find_exact (interest->GetName ());
+  if (entry == m_this->m_pendingInterests.end ())
+    {
+      pair<FilterEntryContainer<DataCallback, Interest>::iterator, bool> status =
+        m_this->m_pendingInterests.insert (interest->GetName (), Create< FilterEntry<DataCallback, Interest> > (interest));
 
-//       entry = status.first;
-//     }
-//   entry->payload ()->AddCallback (rawDataCallback);
+      entry = status.first;
+    }
+  entry->payload ()->AddCallback (onData);
 
-//   m_protocolHanler (packet);
-//   m_transmittedInterests (&interestHeader, this, m_face);
+  ReceiveInterest (interest);
+}
+
+void
+ApiFace::SetInterestFilter (Ptr<const Name> prefix, InterestCallback onInterest)
+{
+  NS_LOG_DEBUG ("== setInterestFilter " << *prefix << " (" << GetNode ()->GetId () << ")");
+
+  FilterEntryContainer<InterestCallback, Name>::iterator entry = m_this->m_expectedInterests.find_exact (*prefix);
+  if (entry == m_this->m_expectedInterests.end ())
+    {
+      pair<FilterEntryContainer<InterestCallback, Name>::iterator, bool> status =
+        m_this->m_expectedInterests.insert (*prefix, Create < FilterEntry<InterestCallback, Name> > (prefix));
+
+      entry = status.first;
+    }
+
+  entry->payload ()->AddCallback (onInterest);
+
+  // creating actual face
+  Ptr<ndn::Fib> fib = GetNode ()->GetObject<ndn::Fib> ();
+  Ptr<ndn::fib::Entry> fibEntry = fib->Add (prefix, this, 0);
+  fibEntry->UpdateStatus (this, ndn::fib::FaceMetric::NDN_FIB_GREEN);
+}
+
+void
+ApiFace::ClearInterestFilter (Ptr<const Name> prefix)
+{
+  FilterEntryContainer<InterestCallback, Name>::iterator entry = m_this->m_expectedInterests.find_exact (*prefix);
+  if (entry == m_this->m_expectedInterests.end ())
+    return;
+
+  entry->payload ()->ClearCallback ();
+  m_this->m_expectedInterests.erase (entry);
+}
+
+void
+ApiFace::Put (Ptr<ContentObject> data)
+{
+  NS_LOG_INFO (">> D " << data->GetName ());
   
-//   return 0;
-// }
+  ReceiveData (data);
+}
 
-// int ApiFace::setInterestFilter (const string &prefix, const InterestCallback &interestCallback)
-// {
-//   NS_LOG_DEBUG ("== setInterestFilter " << prefix << " (" << GetNode ()->GetId () << ")");
-//   Ptr<ndn::Name> name = Create<ndn::Name> (prefix);
 
-//   FilterEntryContainer<InterestCallback>::iterator entry = m_interestCallbacks.find_exact (*name);
-//   if (entry == m_interestCallbacks.end ())
-//     {
-//       pair<FilterEntryContainer<InterestCallback>::iterator, bool> status =
-//         m_interestCallbacks.insert (*name, Create < FilterEntry<InterestCallback> > (name));
 
-//       entry = status.first;
-//     }
 
-//   entry->payload ()->AddCallback (interestCallback);
+///////////////////////////////////////////////
+// private stuff
 
-//   // creating actual face
-//   Ptr<ndn::Fib> fib = GetNode ()->GetObject<ndn::Fib> ();
-//   Ptr<ndn::fib::Entry> fibEntry = fib->Add (name, m_face, 0);
-//   fibEntry->UpdateStatus (m_face, ndn::fib::FaceMetric::NDN_FIB_GREEN);
 
-//   return 0;
-// }
+bool
+ApiFace::SendInterest (Ptr<const Interest> interest)
+{
+  NS_LOG_FUNCTION (this << interest);
 
-// void
-// ApiFace::clearInterestFilter (const std::string &prefix)
-// {
-//   Ptr<ndn::Name> name = Create<ndn::Name> (prefix);
-
-//   FilterEntryContainer<InterestCallback>::iterator entry = m_interestCallbacks.find_exact (*name);
-//   if (entry == m_interestCallbacks.end ())
-//     return;
-
-//   entry->payload ()->ClearCallback ();
-// }
-
-// void
-// ApiFace::OnInterest (const Ptr<const ndn::Interest> &interest, Ptr<Packet> packet)
-// {
-//   ndn::App::OnInterest (interest, packet);
-
-//   // the app cannot set several filters for the same prefix
-//   FilterEntryContainer<InterestCallback>::iterator entry = m_interestCallbacks.longest_prefix_match (interest->GetName ());
-//   if (entry == m_interestCallbacks.end ())
-//     {
-//       _LOG_DEBUG ("No Interest callback set");
-//       return;
-//     }
+  NS_LOG_DEBUG ("<< I " << interest->GetName ());
   
-//   entry->payload ()->m_callback (lexical_cast<string> (interest->GetName ()));  
-// }
+  if (!IsUp ())
+    {
+      return false;
+    }
 
-// void
-// ApiFace::OnContentObject (const Ptr<const ndn::ContentObject> &contentObject,
-//                               Ptr<Packet> payload)
-// {
-//   ndn::App::OnContentObject (contentObject, payload);
-//   NS_LOG_DEBUG ("<< D " << contentObject->GetName ());
+  // the app cannot set several filters for the same prefix
+  FilterEntryContainer<InterestCallback, Name>::iterator entry =
+    m_this->m_expectedInterests.longest_prefix_match (interest->GetName ());
+  if (entry == m_this->m_expectedInterests.end ())
+    {
+      return false;
+    }
+  
+  entry->payload ()->m_callback (entry->payload ()->GetPayload (), interest);
+  return true;
+}
 
-//   FilterEntryContainer<RawDataCallback>::iterator entry = m_dataCallbacks.longest_prefix_match (contentObject->GetName ());
-//   if (entry == m_dataCallbacks.end ())
-//     {
-//       _LOG_DEBUG ("No Data callback set");
-//       return;
-//     }
+bool
+ApiFace::SendData (Ptr<const ContentObject> data)
+{
+  // data has been send out from NDN stack towards the application
+  NS_LOG_DEBUG ("<< D " << data->GetName ());
 
-//   while (entry != m_dataCallbacks.end ())
-//     {
-//       entry->payload ()->m_callback (lexical_cast<string> (contentObject->GetName ()), payload);
-//       m_dataCallbacks.erase (entry);
 
-//       entry = m_dataCallbacks.longest_prefix_match (contentObject->GetName ());
-//     }
-// }
+  NS_LOG_FUNCTION (this << data);
+
+  if (!IsUp ())
+    {
+      return false;
+    }
+
+  FilterEntryContainer<DataCallback, Interest>::iterator entry =
+    m_this->m_pendingInterests.longest_prefix_match (data->GetName ());
+  if (entry == m_this->m_pendingInterests.end ())
+    {
+      return false;
+    }
+
+  while (entry != m_this->m_pendingInterests.end ())
+    {
+      entry->payload ()->m_callback (entry->payload ()->GetPayload (), data);
+      m_this->m_pendingInterests.erase (entry);
+
+      entry = m_this->m_pendingInterests.longest_prefix_match (data->GetName ());
+    }
+  m_this->m_pendingInterests.erase (entry);
+  
+  return true;
+}
+
+std::ostream&
+ApiFace::Print (std::ostream &os) const
+{
+  os << "dev=ApiFace(" << GetId () << ")";
+  return os;
+}
+
 
 }
 }
