134 lines
4.7 KiB
C++
134 lines
4.7 KiB
C++
#pragma once
|
|
|
|
|
|
#include <cstdint>
|
|
#include <cfloat>
|
|
#include <algorithm>
|
|
#include <memory>
|
|
#include <vector>
|
|
#include "device/Device.h"
|
|
#include "registers/MGMT.h"
|
|
#include "Constants.h"
|
|
#include "Port.h"
|
|
|
|
#define FM10K_GET_REGISTER(i, t) i.getType<t>(t::ADDRESS)
|
|
#define FM10K_MAP_REGISTER(i, t) i.mapType<t>(t::ADDRESS)
|
|
#define FM10K_SET_REGISTER(i, t, v) i.setType<t>(t::ADDRESS, v)
|
|
#define FM10K_SET_REGISTER_FIELD(i, t, f, v) \
|
|
auto __f = FM10K_MAP_REGISTER(i, t); \
|
|
__f->fields. f = v
|
|
|
|
#define FM10K_GET_REGISTER_OFFSET(i, t, o) i.getType<t>(t::ADDRESS + o)
|
|
#define FM10K_MAP_REGISTER_OFFSET(i, t, o) i.mapType<t>(t::ADDRESS + o)
|
|
#define FM10K_SET_REGISTER_OFFSET(i, t, o, v) i.setType<t>(t::ADDRESS + o, v)
|
|
#define FM10K_SET_REGISTER_FIELD_OFFSET(i, t, o, f, v) \
|
|
auto __f = FM10K_MAP_REGISTER(i, t, o); \
|
|
__f->fields. f = v
|
|
|
|
namespace FM10K{
|
|
|
|
class FM10K {
|
|
public:
|
|
|
|
explicit FM10K(std::unique_ptr<Device> device);
|
|
|
|
bool valid() const{
|
|
return m_device->valid();
|
|
}
|
|
|
|
template<typename T> volatile T* mapType(uint32_t address) const {
|
|
return reinterpret_cast<volatile T*>(m_device->map32(address));
|
|
}
|
|
|
|
template<typename T> volatile T* mapRegister(uint32_t offset = 0) const{
|
|
return FM10K_MAP_REGISTER_OFFSET((*this), T, offset);
|
|
}
|
|
|
|
template<typename T> T getType(uint32_t address) const {
|
|
static_assert(sizeof(T) == 4 || sizeof(T) == 8, "Invalid type for FM10K::getType");
|
|
T t;
|
|
if(sizeof(T) == 4){
|
|
t.value = m_device->get32(address);
|
|
}else if(sizeof(T) == 8){
|
|
t = reinterpret_cast<T>(m_device->get64(address));
|
|
}
|
|
return std::move(t);
|
|
}
|
|
|
|
template<typename T> void setType(uint32_t address, const T& t) const {
|
|
static_assert(sizeof(T) == 4 || sizeof(T) == 8, "Invalid type for FM10K::setType");
|
|
if(sizeof(T) == 4){
|
|
m_device->set32(address, t.value);
|
|
}else if(sizeof(T) == 8){
|
|
m_device->set64(address, reinterpret_cast<uint64_t>(t));
|
|
}
|
|
|
|
return std::move(t);
|
|
}
|
|
|
|
uint32_t getValue(uint32_t address) const {
|
|
return m_device->get32(address);
|
|
}
|
|
|
|
void setValue(uint32_t address, uint32_t value) const {
|
|
m_device->set32(address, value);
|
|
}
|
|
|
|
struct HardwareInformation{
|
|
enum class Family{
|
|
FM10000 = 0xAE21
|
|
};
|
|
enum class Model{
|
|
// FMxppbb, x = series number, pp = Number of PCIe data ports, bb = Ethernet port bandwidth
|
|
//
|
|
// +- Max Ethernet Port Usage -+- PCIe Data -+- Estimated -+-----+--------------------------+
|
|
// | 100G | 40G | 10G | SGMII | Ports | WC Power | ROM | Use Cases |
|
|
// +-------+-----+-----+-------+-------------+-------------+-----+--------------------------+
|
|
FM10840 = 0, // | 4 | 9 | 36 | 36 | 8x4, 4x8 | 50 W | Yes | High perf compute fabric |
|
|
FM10420 = 1, // | 2 | 2 | 8 | 8 | 4x4, 2x8 | 38 W | Yes | Low cost compute fabric |
|
|
FM10824 = 2, // | 0 | 6 | 24 | 36 | 8x4, 4x8 | 43 W | No | 10G/40G/100GbE NIC |
|
|
FM10064 = 3, // | 6 | 9 | 36 | 36 | 0 | 47 W | No | Microserver switch |
|
|
FM10036 = 4 // | 0 | 0 | 0 | 0 | 0 | 39 W | No | Low cost 10GbE switch |
|
|
// +-------+-----+-----+-------+-------------+-------------+-----+--------------------------+
|
|
};
|
|
enum class ChipVersion{
|
|
A0 = 0,
|
|
B0 = 1
|
|
};
|
|
Family family;
|
|
Model model;
|
|
ChipVersion chipVersion;
|
|
};
|
|
const HardwareInformation& getHardwareInformation() const;
|
|
std::string getHardwareInformationString() const;
|
|
|
|
static void wait(uint32_t microseconds);
|
|
static void wait_ns(uint32_t nanoseconds);
|
|
|
|
Port& addPort(uint32_t logicalPort, uint32_t physicalPort){
|
|
m_ports.emplace_back(m_ports.size(), logicalPort, physicalPort);
|
|
return m_ports.back();
|
|
}
|
|
|
|
Port* getPort(uint32_t portIndex){
|
|
return portIndex < m_ports.size() ? &m_ports.back() : nullptr;
|
|
}
|
|
|
|
bool initializationSequence() const;
|
|
|
|
bool isPEPEnabled(uint8_t pep) const;
|
|
|
|
protected:
|
|
|
|
private:
|
|
std::unique_ptr<Device> m_device;
|
|
HardwareInformation m_hwInfo{};
|
|
std::vector<Port> m_ports;
|
|
void* m_ies = nullptr;
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|