1 //  Copyright (c) 2015-2016 John Biddiscombe
2 //
3 //  Distributed under the Boost Software License, Version 1.0. (See accompanying
4 //  file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
5 
6 #ifndef HPX_PARCELSET_POLICIES_VERBS_PROTECTION_DOMAIN
7 #define HPX_PARCELSET_POLICIES_VERBS_PROTECTION_DOMAIN
8 
9 #include <plugins/parcelport/parcelport_logging.hpp>
10 #include <plugins/parcelport/verbs/rdma/rdma_error.hpp>
11 //
12 #include <infiniband/verbs.h>
13 //
14 #include <memory>
15 
16 namespace hpx {
17 namespace parcelset {
18 namespace policies {
19 namespace verbs
20 {
21 
22     struct verbs_protection_domain
23     {
24         // ---------------------------------------------------------------------------
verbs_protection_domainhpx::parcelset::policies::verbs::verbs_protection_domain25         verbs_protection_domain(struct ibv_context *context)
26         {
27             // Validate context pointer (since ibv_ functions won't check it).
28             if (context == nullptr) {
29                 LOG_ERROR_MSG("error with context pointer " << context
30                     << " when constructing protection domain");
31                 throw std::runtime_error("Null context in protection domain");
32             }
33 
34             // Allocate a protection domain.
35             pd_ = ibv_alloc_pd(context);
36             if (pd_ == nullptr) {
37                 LOG_ERROR_MSG("error allocating protection domain");
38                 throw std::runtime_error("error allocating protection domain");
39             }
40             LOG_DEBUG_MSG("allocated protection domain " << pd_->handle);
41         }
42 
43         // ---------------------------------------------------------------------------
~verbs_protection_domainhpx::parcelset::policies::verbs::verbs_protection_domain44         ~verbs_protection_domain()
45         {
46             if (pd_ != nullptr) {
47                 uint32_t handle = pd_->handle;
48                 int err = ibv_dealloc_pd(pd_);
49                 if (err == 0) {
50                     pd_ = nullptr;
51                     LOG_DEBUG_MSG("deallocated protection domain " << handle);
52                 }
53                 else {
54                     LOG_ERROR_MSG("error deallocating protection domain " << handle
55                         << ": " <<  rdma_error::error_string(errno));
56                 }
57             }
58         }
59 
60         // ---------------------------------------------------------------------------
61         // get the infiniband verbs protection domain object
getDomainhpx::parcelset::policies::verbs::verbs_protection_domain62         struct ibv_pd *getDomain(void) const {
63             return pd_;
64         }
65 
66         // ---------------------------------------------------------------------------
67         // get the infiniband verbs protection domain handle
get_handlehpx::parcelset::policies::verbs::verbs_protection_domain68         uint32_t get_handle(void) const {
69             return pd_ != nullptr ? pd_->handle : 0;
70         }
71 
72     private:
73 
74         // Protection domain.
75         struct ibv_pd *pd_;
76 
77     };
78 
79     // Smart pointer for verbs_protection_domain object.
80     typedef std::shared_ptr<verbs_protection_domain> verbs_protection_domain_ptr;
81 
82 }}}}
83 
84 #endif
85 
86