diff options
| author | Nicholas Corgan <nick.corgan@ettus.com> | 2015-08-05 08:46:28 -0700 | 
|---|---|---|
| committer | Martin Braun <martin.braun@ettus.com> | 2015-08-05 13:04:04 -0700 | 
| commit | bb62ab84fdad6f7cf18ea55d395dfbd7f11ed79d (patch) | |
| tree | ab9bb3a78f10661e12b832c9c341d027463739ba /host/lib/usrp | |
| parent | c3c9513b9b5f67afe4233659222fdfc5bbb2511c (diff) | |
| download | uhd-bb62ab84fdad6f7cf18ea55d395dfbd7f11ed79d.tar.gz uhd-bb62ab84fdad6f7cf18ea55d395dfbd7f11ed79d.tar.bz2 uhd-bb62ab84fdad6f7cf18ea55d395dfbd7f11ed79d.zip | |
image_loader: force user to specify device
* On utility level, force user to use --args=type=foo
* In each loader, throw an error if args are ambiguous
Diffstat (limited to 'host/lib/usrp')
| -rw-r--r-- | host/lib/usrp/b200/b200_image_loader.cpp | 33 | ||||
| -rw-r--r-- | host/lib/usrp/usrp2/n200_image_loader.cpp | 80 | ||||
| -rw-r--r-- | host/lib/usrp/x300/x300_image_loader.cpp | 32 | 
3 files changed, 106 insertions, 39 deletions
| diff --git a/host/lib/usrp/b200/b200_image_loader.cpp b/host/lib/usrp/b200/b200_image_loader.cpp index 87010244c..9eaeeff63 100644 --- a/host/lib/usrp/b200/b200_image_loader.cpp +++ b/host/lib/usrp/b200/b200_image_loader.cpp @@ -40,27 +40,50 @@ static b200_iface::sptr get_b200_iface(const image_loader::image_loader_args_t &                                         bool user_specified){      std::vector<usb_device_handle::sptr> dev_handles = get_b200_device_handles(image_loader_args.args); +    std::vector<usb_device_handle::sptr> applicable_dev_handles;      b200_iface::sptr iface; +    mboard_eeprom_t eeprom; // Internal use      if(dev_handles.size() > 0){          BOOST_FOREACH(usb_device_handle::sptr dev_handle, dev_handles){              if(dev_handle->firmware_loaded()){                  iface = b200_iface::make(usb_control::make(dev_handle,0)); -                mb_eeprom = mboard_eeprom_t(*iface, "B200"); +                eeprom = mboard_eeprom_t(*iface, "B200");                  if(user_specified){                      if(image_loader_args.args.has_key("serial") and -                       mb_eeprom.get("serial") != image_loader_args.args.get("serial")){ +                       eeprom.get("serial") != image_loader_args.args.get("serial")){                             continue;                      }                      if(image_loader_args.args.has_key("name") and -                       mb_eeprom.get("name") != image_loader_args.args.get("name")){ +                       eeprom.get("name") != image_loader_args.args.get("name")){                             continue;                      } -                    return iface; +                    applicable_dev_handles.push_back(dev_handle);                  } -                else return iface; // Just return first found +                else applicable_dev_handles.push_back(dev_handle);              }          } + +        // At this point, we should have a single B2XX +        if(applicable_dev_handles.size() == 1){ +            mb_eeprom = eeprom; +            return iface; +        } +        else if(applicable_dev_handles.size() > 1){ +            std::string err_msg = "Could not resolve given args to a single B2XX device.\n" +                                  "Applicable devices:\n"; + +            BOOST_FOREACH(usb_device_handle::sptr dev_handle, applicable_dev_handles){ +                eeprom = mboard_eeprom_t(*b200_iface::make(usb_control::make(dev_handle,0)), "B200"); +                err_msg += str(boost::format(" * %s (serial=%s)\n") +                               % B2X0_STR_NAMES.get(get_b200_type(mb_eeprom), "B2XX") +                               % mb_eeprom.get("serial")); +            } + +            err_msg += "\nSpecify one of these devices with the given args to load an image onto it."; + +            throw uhd::runtime_error(err_msg); +         }      }      // No applicable devices found, return empty sptr so we can exit diff --git a/host/lib/usrp/usrp2/n200_image_loader.cpp b/host/lib/usrp/usrp2/n200_image_loader.cpp index ce956c22c..29bec8b4a 100644 --- a/host/lib/usrp/usrp2/n200_image_loader.cpp +++ b/host/lib/usrp/usrp2/n200_image_loader.cpp @@ -210,36 +210,62 @@ static uhd::device_addr_t n200_find(const image_loader::image_loader_args_t &ima                            image_loader_args.args.has_key("name");      uhd::device_addrs_t found = usrp2_find(image_loader_args.args); -    if(found.size() > 0){ -        uhd::device_addr_t ret = found[0]; - -        /* -         * Make sure the device found is an N-Series and not a USRP2. A USRP2 -         * will not respond to this query. If the user supplied specific -         * arguments that led to a USRP2, throw an error. -         */ -        udp_simple::sptr rev_xport = udp_simple::make_connected( -                                         ret["addr"], -                                         BOOST_STRINGIZE(N200_UDP_FW_UPDATE_PORT) -                                     ); +    if(found.size() > 0){ +        uhd::device_addrs_t n200_found; +        udp_simple::sptr rev_xport;          n200_fw_update_data_t pkt_out;          boost::uint8_t data_in[udp_simple::mtu];          const n200_fw_update_data_t *pkt_in = reinterpret_cast<const n200_fw_update_data_t*>(data_in); +        size_t len = 0; -        size_t len = n200_send_and_recv(rev_xport, GET_HW_REV_CMD, &pkt_out, data_in); -        if(n200_response_matches(pkt_in, GET_HW_REV_ACK, len)){ -            boost::uint32_t rev = ntohl(pkt_in->data.hw_rev); -            ret["hw_rev"] = n200_filename_map.get(rev, "n2xx"); -            return ret; +        /* +         * Filter out any USRP2 devices by sending a query over the +         * UDP update port. Only N-Series devices will respond to +         * this query. If the user supplied specific arguments that +         * led to a USRP2, throw an error. +         */ +        BOOST_FOREACH(const uhd::device_addr_t &dev, found){ +            rev_xport = udp_simple::make_connected( +                            dev.get("addr"), +                            BOOST_STRINGIZE(N200_UDP_FW_UPDATE_PORT) +                        ); + +            len = n200_send_and_recv(rev_xport, GET_HW_REV_CMD, &pkt_out, data_in); +            if(n200_response_matches(pkt_in, GET_HW_REV_ACK, len)){ +                boost::uint32_t rev = ntohl(pkt_in->data.hw_rev); +                std::string hw_rev = n200_filename_map.get(rev, "n2xx"); + +                n200_found.push_back(dev); +                n200_found[n200_found.size()-1]["hw_rev"] = hw_rev; +            } +            else if(len > offsetof(n200_fw_update_data_t, data) and ntohl(pkt_in->id) != GET_HW_REV_ACK){ +                throw uhd::runtime_error(str(boost::format("Received invalid reply %d from device.") +                                             % ntohl(pkt_in->id))); +            } +            else if(user_specified){ +                // At this point, we haven't received any response, so assume it's a USRP2 +                print_usrp2_error(image_loader_args); +            }          } -        else if(len > offsetof(n200_fw_update_data_t, data) and ntohl(pkt_in->id) != GET_HW_REV_ACK){ -            throw uhd::runtime_error(str(boost::format("Received invalid reply %d from device.") -                                         % ntohl(pkt_in->id))); + +        // At this point, we should have a single N-Series device +        if(n200_found.size() == 1){ +            return n200_found[0];          } -        else if(user_specified){ -            // At this point, we haven't received any response, so assume it's a USRP2 -            print_usrp2_error(image_loader_args); +        else if(n200_found.size() > 1){ +            std::string err_msg = "Could not resolve given args to a single N-Series device.\n" +                                  "Applicable devices:\n"; + +            BOOST_FOREACH(const uhd::device_addr_t &dev, n200_found){ +                err_msg += str(boost::format("* %s (addr=%s)\n") +                               % dev.get("hw_rev") +                               % dev.get("addr")); +            } + +            err_msg += "\nSpecify one of these devices with the given args to load an image onto it."; + +            throw uhd::runtime_error(err_msg);          }      } @@ -259,7 +285,7 @@ static void n200_validate_firmware_image(n200_session_t &session){      session.max_size = N200_FW_MAX_SIZE_BYTES;      if(session.size > session.max_size){ -        throw uhd::runtime_error(str(boost::format("The specified FPGA image is too large: %d vs. %d") +        throw uhd::runtime_error(str(boost::format("The specified firmware image is too large: %d vs. %d")                                       % session.size % session.max_size));      } @@ -559,11 +585,15 @@ static std::string nice_name(const std::string &fw_rev){  }  static bool n200_image_loader(const image_loader::image_loader_args_t &image_loader_args){ +    if(!image_loader_args.load_firmware and !image_loader_args.load_fpga){ +        return false; +    } +      // See if any N2x0 with the given args is found      // This will throw if specific args lead to a USRP2      n200_session_t session;      session.dev_addr = n200_find(image_loader_args); -    if(session.dev_addr.size() == 0 or (!image_loader_args.load_firmware and !image_loader_args.load_fpga)){ +    if(session.dev_addr.size() == 0){          return false;      } diff --git a/host/lib/usrp/x300/x300_image_loader.cpp b/host/lib/usrp/x300/x300_image_loader.cpp index 321309868..9ec8a2e13 100644 --- a/host/lib/usrp/x300/x300_image_loader.cpp +++ b/host/lib/usrp/x300/x300_image_loader.cpp @@ -158,17 +158,31 @@ static void x300_validate_image(x300_session_t &session){  static void x300_setup_session(x300_session_t &session,                                 const device_addr_t &args,                                 const std::string &filepath){ -    device_addr_t find_args; -    find_args["type"] = "x300"; -    if(args.has_key("name")) find_args["name"] = args["name"]; -    if(args.has_key("serial")) find_args["serial"] = args["serial"]; -    if(args.has_key("ip-addr")) find_args["addr"] = args["ip-addr"]; -    else if(args.has_key("resource")) find_args["resource"] = args["resource"]; -      device_addrs_t devs = x300_find(args); -    session.found = (devs.size() > 0); -    if(!session.found) return; +    if(devs.size() == 0){ +        session.found = false; +        return; +    } +    else if(devs.size() > 1){ +        std::string err_msg = "Could not resolve given args to a single X-Series device.\n" +                              "Applicable devices:\n"; + +        BOOST_FOREACH(const uhd::device_addr_t &dev, devs){ +            std::string identifier = dev.has_key("addr") ? "addr" +                                                         : "resource"; + +            err_msg += str(boost::format(" * %s (%s=%s)\n") +                           % dev.get("product", "X3XX") +                           % identifier +                           % dev.get(identifier)); +        } + +        err_msg += "\nSpecify one of these devices with the given args to load an image onto it."; + +        throw uhd::runtime_error(err_msg); +    } +    session.found = true;      session.dev_addr = devs[0];      session.ethernet = session.dev_addr.has_key("addr");      if(session.ethernet){ | 
