예제 #1
0
 def _gen_error(self,buf,path):
     """Sadly the kernel can return EINVAL if it could not process the MAD,
     eg if you ask for PortInfo of the local CA with an invalid attributeID
     the Mellanox driver will return EINVAL rather than construct an error
     MAD. I consider this to be a bug in the kernel, but we fix it here
     by constructing an error MAD."""
     buf = copy.copy(buf);
     rmatch = self._get_reply_match_key(buf);
     buf[3] = rmatch[1];
     buf[4] = 0;
     buf[5] = IBA.MAD_STATUS_INVALID_ATTR_OR_MODIFIER; # Guessing.
     path = path.copy();
     path.reverse();
     return (buf,path);
예제 #2
0
    def advance_dr(self,path,portIdx):
        """Create a new :class:`~rdma.path.IBDRPath` that goes to the
        device connected to *port_idx* of *path*."""
        # LID route to a HCA followed by DR route after does not work, in the local
        # host case I think this is a kernel bug, but other cases seem to be as the
        # spec intends.
        drPath = getattr(path,"drPath","\0") + chr(portIdx);
        if len(drPath) > 64:
            raise rdma.RDMAError("DR path length limit exceeded, %r"%(drPath));
        if (path.DLID == path.end_port.lid and
            path.DLID != IBA.LID_PERMISSIVE and
            path.DLID != 0):
            # Local loopback
            return rdma.path.IBDRPath(path.end_port,drPath=drPath);
        else:
            if isinstance(path,rdma.path.IBDRPath):
                ret = path.copy(drPath=drPath);
            else:
                ret = rdma.path.IBDRPath(path.end_port,
                                         SLID=path.SLID,
                                         drSLID=path.SLID,
                                         DLID=path.DLID,
                                         drPath=drPath,
                                         retries=path.retries);

            ep = self.path_to_port(path);
            if ep is not None and not isinstance(ep.parent,Switch):
                # If we are DR'ing from a non-CA then the only possible legal
                # thing is to go back out the same port. Dropping the last entry
                # from the DR list is the same thing.
                if len(drPath) >= 3 and ep.port_id == portIdx:
                    ret.drPath = drPath[:-2];
                else:
                    # Hum, we know this will fail, try and fix it up with our topology
                    # database..
                    np = self.topology.get(ep.parent.get_port(portIdx));
                    if np is not None:
                        ret = self.get_path_smp(path,np.to_end_port());

                # When we eat the DR path like this it breaks
                # localPortNum, but since we are going in and out of the
                # same port we can just record what it should have been
                # here.
                ret._cached_subnet_localPortNum = ord(drPath[-2]);

            return ret;
예제 #3
0
    def _gen_error(self,buf,path):
        """Sadly the kernel can return EINVAL if it could not process the MAD,
        eg if you ask for PortInfo of the local CA with an invalid attributeID
        the Mellanox driver will return EINVAL rather than construct an error
        MAD. I consider this to be a bug in the kernel, but we fix it here
        by constructing an error MAD."""
        buf = copy.copy(buf);

        meth = buf[3];
        if meth == IBA.MAD_METHOD_SET:
            meth = IBA.MAD_METHOD_GET_RESP;
        else:
            meth = meth | IBA.MAD_METHOD_RESPONSE;
        buf[3] = meth;

        buf[4] = 0;
        buf[5] = IBA.MAD_STATUS_INVALID_ATTR_OR_MODIFIER; # Guessing.
        path = path.copy();
        path.reverse();
        return (buf,path);
예제 #4
0
    def _gen_error(self, buf, path):
        """Sadly the kernel can return EINVAL if it could not process the MAD,
        eg if you ask for PortInfo of the local CA with an invalid attributeID
        the Mellanox driver will return EINVAL rather than construct an error
        MAD. I consider this to be a bug in the kernel, but we fix it here
        by constructing an error MAD."""
        buf = copy.copy(buf)

        meth = buf[3]
        if meth == IBA.MAD_METHOD_SET:
            meth = IBA.MAD_METHOD_GET_RESP
        else:
            meth = meth | IBA.MAD_METHOD_RESPONSE
        buf[3] = meth

        buf[4] = 0
        buf[5] = IBA.MAD_STATUS_INVALID_ATTR_OR_MODIFIER
        # Guessing.
        path = path.copy()
        path.reverse()
        return (buf, path)