1 //
2 // Copyright 2018 Ettus Research, a National Instruments Company
3 //
4 // SPDX-License-Identifier: GPL-3.0-or-later
5 //
6 
7 #include <uhd/exception.hpp>
8 #include <uhdlib/rfnoc/epid_allocator.hpp>
9 
10 using namespace uhd;
11 using namespace uhd::rfnoc;
12 
epid_allocator(sep_id_t start_epid)13 epid_allocator::epid_allocator(sep_id_t start_epid) : _next_epid(start_epid) {}
14 
allocate_epid(const sep_addr_t & addr)15 sep_id_t epid_allocator::allocate_epid(const sep_addr_t& addr)
16 {
17     std::lock_guard<std::mutex> lock(_mutex);
18 
19     if (_epid_map.count(addr) == 0) {
20         sep_id_t new_epid   = _next_epid++;
21         _epid_map[addr]     = new_epid;
22         _addr_map[new_epid] = addr;
23         return new_epid;
24     } else {
25         return _epid_map.at(addr);
26     }
27 }
28 
allocate_epid(const sep_addr_t & addr,mgmt::mgmt_portal & mgmt_portal,chdr_ctrl_xport & xport)29 sep_id_t epid_allocator::allocate_epid(
30     const sep_addr_t& addr, mgmt::mgmt_portal& mgmt_portal, chdr_ctrl_xport& xport)
31 {
32     std::lock_guard<std::mutex> lock(_mutex);
33 
34     if (_epid_map.count(addr) == 0) {
35         sep_id_t new_epid   = _next_epid++;
36         _epid_map[addr]     = new_epid;
37         _addr_map[new_epid] = addr;
38         mgmt_portal.initialize_endpoint(xport, addr, new_epid);
39         return new_epid;
40     } else {
41         sep_id_t epid = _epid_map.at(addr);
42         mgmt_portal.register_endpoint(addr, epid);
43         return epid;
44     }
45 }
46 
get_epid(const sep_addr_t & addr)47 sep_id_t epid_allocator::get_epid(const sep_addr_t& addr)
48 {
49     std::lock_guard<std::mutex> lock(_mutex);
50 
51     if (_epid_map.count(addr) != 0) {
52         return _epid_map.at(addr);
53     } else {
54         throw uhd::lookup_error(
55             "An EPID has not been allocated for the requested endpoint");
56     }
57 }
58 
lookup_addr(const sep_id_t & epid) const59 sep_addr_t epid_allocator::lookup_addr(const sep_id_t& epid) const
60 {
61     std::lock_guard<std::mutex> lock(_mutex);
62 
63     if (_addr_map.count(epid) > 0) {
64         return _addr_map.at(epid);
65     } else {
66         throw uhd::lookup_error("The specified EPID has not been allocated");
67     }
68 }
69 
deallocate_epid(sep_id_t)70 void epid_allocator::deallocate_epid(sep_id_t)
71 {
72     std::lock_guard<std::mutex> lock(_mutex);
73     // TODO: Nothing to do for deallocate.
74     //      With the current counter approach we assume that we will not run out of EPIDs
75 }
76