aboutsummaryrefslogtreecommitdiffstats
path: root/host/lib
diff options
context:
space:
mode:
authorAshish Chaudhari <ashish@ettus.com>2016-01-08 13:29:13 -0800
committerAshish Chaudhari <ashish@ettus.com>2016-01-08 13:29:13 -0800
commitb025e7ec71839da95c94784759de40482e7d77f1 (patch)
treeb815eea43f94083578b2d3bec2a8857e6570b7e9 /host/lib
parent2326da0dd107e2a784771ff163e3b33be45300ea (diff)
downloaduhd-b025e7ec71839da95c94784759de40482e7d77f1.tar.gz
uhd-b025e7ec71839da95c94784759de40482e7d77f1.tar.bz2
uhd-b025e7ec71839da95c94784759de40482e7d77f1.zip
n230: Added hardware compatibility version checks to UHD
Diffstat (limited to 'host/lib')
-rw-r--r--host/lib/usrp/n230/n230_eeprom_manager.cpp27
-rw-r--r--host/lib/usrp/n230/n230_impl.cpp28
2 files changed, 53 insertions, 2 deletions
diff --git a/host/lib/usrp/n230/n230_eeprom_manager.cpp b/host/lib/usrp/n230/n230_eeprom_manager.cpp
index ed40b47be..40f501ef9 100644
--- a/host/lib/usrp/n230/n230_eeprom_manager.cpp
+++ b/host/lib/usrp/n230/n230_eeprom_manager.cpp
@@ -65,10 +65,22 @@ const mboard_eeprom_t& n230_eeprom_manager::read_mb_eeprom()
const n230_eeprom_map_t* map_ptr = reinterpret_cast<const n230_eeprom_map_t*>(_response.data);
const n230_eeprom_map_t& map = *map_ptr;
+ uint16_t ver_major = uhd::htonx<boost::uint16_t>(map.data_version_major);
+ uint16_t ver_minor = uhd::htonx<boost::uint16_t>(map.data_version_minor);
+
_mb_eeprom["product"] = boost::lexical_cast<std::string>(
uhd::htonx<boost::uint16_t>(map.hw_product));
_mb_eeprom["revision"] = boost::lexical_cast<std::string>(
uhd::htonx<boost::uint16_t>(map.hw_revision));
+ //The revision_compat field does not exist in version 1.0
+ //EEPROM version 1.0 will only exist on HW revision 1 so it is safe to set
+ //revision_compat = revision
+ if (ver_major == 1 and ver_minor == 0) {
+ _mb_eeprom["revision_compat"] = _mb_eeprom["revision"];
+ } else {
+ _mb_eeprom["revision_compat"] = boost::lexical_cast<std::string>(
+ uhd::htonx<boost::uint16_t>(map.hw_revision_compat));
+ }
_mb_eeprom["serial"] = _bytes_to_string(
map.serial, N230_EEPROM_SERIAL_LEN);
@@ -104,6 +116,15 @@ void n230_eeprom_manager::write_mb_eeprom(const mboard_eeprom_t& eeprom)
memcpy(map_ptr, _response.data, sizeof(n230_eeprom_map_t));
n230_eeprom_map_t& map = *map_ptr;
+ // Automatic version upgrade handling
+ uint16_t old_ver_major = uhd::htonx<boost::uint16_t>(map.data_version_major);
+ uint16_t old_ver_minor = uhd::htonx<boost::uint16_t>(map.data_version_minor);
+
+ //The revision_compat field does not exist for version 1.0 so force write it
+ //EEPROM version 1.0 will only exist on HW revision 1 so it is safe to set
+ //revision_compat = revision for the upgrade
+ bool force_write_version_compat = (old_ver_major == 1 and old_ver_minor == 0);
+
map.data_version_major = uhd::htonx<boost::uint16_t>(N230_EEPROM_VER_MAJOR);
map.data_version_minor = uhd::htonx<boost::uint16_t>(N230_EEPROM_VER_MINOR);
@@ -115,6 +136,12 @@ void n230_eeprom_manager::write_mb_eeprom(const mboard_eeprom_t& eeprom)
map.hw_revision = uhd::htonx<boost::uint16_t>(
boost::lexical_cast<boost::uint16_t>(_mb_eeprom["revision"]));
}
+ if (_mb_eeprom.has_key("revision_compat")) {
+ map.hw_revision_compat = uhd::htonx<boost::uint16_t>(
+ boost::lexical_cast<boost::uint16_t>(_mb_eeprom["revision_compat"]));
+ } else if (force_write_version_compat) {
+ map.hw_revision_compat = map.hw_revision;
+ }
if (_mb_eeprom.has_key("serial")) {
_string_to_bytes(_mb_eeprom["serial"], N230_EEPROM_SERIAL_LEN, map.serial);
}
diff --git a/host/lib/usrp/n230/n230_impl.cpp b/host/lib/usrp/n230/n230_impl.cpp
index a0094d573..789c6ebd5 100644
--- a/host/lib/usrp/n230/n230_impl.cpp
+++ b/host/lib/usrp/n230/n230_impl.cpp
@@ -181,13 +181,37 @@ n230_impl::n230_impl(const uhd::device_addr_t& dev_addr)
//TODO: Only supports one motherboard per device class.
const fs_path mb_path = "/mboards/0";
- //Initialize subsystems
+ //Initialize addresses
std::vector<std::string> ip_addrs(1, dev_addr["addr"]);
if (dev_addr.has_key("secondary-addr")) {
ip_addrs.push_back(dev_addr["secondary-addr"]);
}
- _resource_mgr = boost::make_shared<n230_resource_manager>(ip_addrs, _dev_args.get_safe_mode());
+
+ //Read EEPROM and perform version checks before talking to HW
_eeprom_mgr = boost::make_shared<n230_eeprom_manager>(ip_addrs[0]);
+ const mboard_eeprom_t& mb_eeprom = _eeprom_mgr->get_mb_eeprom();
+ bool recover_mb_eeprom = dev_addr.has_key("recover_mb_eeprom");
+ if (recover_mb_eeprom) {
+ UHD_MSG(warning) << "UHD is operating in EEPROM Recovery Mode which disables hardware version "
+ "checks.\nOperating in this mode may cause hardware damage and unstable "
+ "radio performance!"<< std::endl;
+ }
+ boost::uint16_t hw_rev = boost::lexical_cast<boost::uint16_t>(mb_eeprom["revision"]);
+ boost::uint16_t hw_rev_compat = boost::lexical_cast<boost::uint16_t>(mb_eeprom["revision_compat"]);
+ if (not recover_mb_eeprom) {
+ if (hw_rev_compat > N230_HW_REVISION_COMPAT) {
+ throw uhd::runtime_error(str(boost::format(
+ "Hardware is too new for this software. Please upgrade to a driver that supports hardware revision %d.")
+ % hw_rev));
+ } else if (hw_rev < N230_HW_REVISION_MIN) { //Compare min against the revision (and not compat) to give us more leeway for partial support for a compat
+ throw uhd::runtime_error(str(boost::format(
+ "Software is too new for this hardware. Please downgrade to a driver that supports hardware revision %d.")
+ % hw_rev));
+ }
+ }
+
+ //Initialize all subsystems
+ _resource_mgr = boost::make_shared<n230_resource_manager>(ip_addrs, _dev_args.get_safe_mode());
_stream_mgr = boost::make_shared<n230_stream_manager>(_dev_args, _resource_mgr, _tree);
//Build property tree