⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 routert.cc

📁 Click is a modular router toolkit. To use it you ll need to know how to compile and install the sof
💻 CC
📖 第 1 页 / 共 3 页
字号:
    // update port count    if (_elements[e]->_noutputs == port + 1)	update_noutputs(e);}voidRouterT::unlink_connection_to(int c){    int e = _conn[c].to_eindex();    int port = _conn[c].to_port();    // find previous connection    int prev = -1;    int trav = _first_conn[e][end_to];    while (trav >= 0 && trav != c) {	prev = trav;	trav = _conn[trav].next_to();    }    assert(trav == c);    // unlink this connection    if (prev < 0)	_first_conn[e][end_to] = _conn[trav].next_to();    else	_conn[prev]._next[end_to] = _conn[trav].next_to();    // update port count    if (_elements[e]->_ninputs == port + 1)	update_ninputs(e);}voidRouterT::free_connection(int c){    _conn[c]._end[end_from].element = 0;	// kill();    _conn[c]._next[end_from] = _free_conn;    _free_conn = c;}voidRouterT::kill_connection(const conn_iterator &ci){    if (ci != end_connections()) {	assert(ci._conn && ci._conn >= _conn.begin() && ci._conn < _conn.end());	int c = ci._conn - _conn.begin();	if (ci->live()) {	    unlink_connection_from(c);	    unlink_connection_to(c);	    free_connection(c);	}    }}voidRouterT::kill_bad_connections(){    for (conn_iterator ci = begin_connections(); ci != end_connections(); ++ci)	if (ci->from_element()->dead() || ci->to_element()->dead())	    kill_connection(ci);}voidRouterT::change_connection_from(int c, PortT h){    assert(h.router() == this);    unlink_connection_from(c);    _conn[c]._end[end_from] = h;    if (h.port >= h.element->_noutputs)	h.element->_noutputs = h.port + 1;    int ei = h.eindex();    _conn[c]._next[end_from] = _first_conn[ei][end_from];    _first_conn[ei][end_from] = c;}voidRouterT::change_connection_to(int c, PortT h){    assert(h.router() == this);    unlink_connection_to(c);    _conn[c]._end[end_to] = h;    if (h.port >= h.element->ninputs())	h.element->set_ninputs(h.port + 1);    int ei = h.eindex();    _conn[c]._next[end_to] = _first_conn[ei][end_to];    _first_conn[ei][end_to] = c;}RouterT::conn_iteratorRouterT::begin_connections_touching(int eindex, int port, bool isoutput) const{    assert(eindex >= 0 && eindex < nelements());    int c = _first_conn[eindex][isoutput];    if (port >= 0) {	while (c >= 0 && _conn[c].port(isoutput) != port)	    c = _conn[c].next(isoutput);	port = (isoutput ? port + 2 : -port - 2);    } else	port = (isoutput ? 1 : -1);    return (c >= 0 ? conn_iterator(&_conn[c], port) : conn_iterator());}voidRouterT::conn_iterator::complex_step(const RouterT *router){    int c = _conn - router->_conn.begin();    assert(c >= 0 && c < router->_conn.size());    if (_by == 0)	++c;    else if (_by >= 1) {	c = _conn->next_from();	while (c >= 0 && _by > 1 && router->_conn[c].from_port() != _by - 2)	    c = router->_conn[c].next_from();    } else {	c = _conn->next_to();	while (c >= 0 && _by < -1 && router->_conn[c].to_port() != -_by - 2)	    c = router->_conn[c].next_to();    }    if (c == router->_conn.size() || c < 0)	_conn = 0;    else	_conn = &router->_conn[c];}intRouterT::find_connection(const PortT &hfrom, const PortT &hto) const{    assert(hfrom.router() == this && hto.router() == this);    int c = _first_conn[hfrom.eindex()][end_from];    while (c >= 0) {	if (_conn[c].from() == hfrom && _conn[c].to() == hto)	    break;	c = _conn[c].next_from();    }    return c;}voidRouterT::find_connections_touching(ElementT *e, bool isoutput, Vector<int> &v) const{    assert(e->router() == this);    int c = _first_conn[e->eindex()][isoutput];    v.clear();    while (c >= 0) {	v.push_back(c);	c = _conn[c].next(isoutput);    }}intRouterT::find_connection_id_touching(const PortT &port, bool isoutput) const{    assert(port.router() == this);    int c = _first_conn[port.eindex()][isoutput];    int p = port.port;    int result = -1;    while (c >= 0) {	if (_conn[c].port(isoutput) == p) {	    if (result == -1)		result = c;	    else		return -2;	}	c = _conn[c].next(isoutput);    }    return result;}voidRouterT::find_connections_touching(const PortT &port, bool isoutput, Vector<PortT> &v, bool clear) const{    assert(port.router() == this);    int c = _first_conn[port.eindex()][isoutput];    int p = port.port;    if (clear)	v.clear();    while (c >= 0) {	if (_conn[c].port(isoutput) == p)	    v.push_back(_conn[c].end(!isoutput));	c = _conn[c].next(isoutput);    }}voidRouterT::find_connections_touching(const PortT &port, bool isoutput, Vector<int> &v) const{    assert(port.router() == this);    int c = _first_conn[port.eindex()][isoutput];    int p = port.port;    v.clear();    while (c >= 0) {	if (_conn[c].port(isoutput) == p)	    v.push_back(c);	c = _conn[c].next(isoutput);    }}voidRouterT::find_connection_vector_touching(ElementT *e, bool isoutput, Vector<int> &v) const{    assert(e->router() == this);    v.clear();    int c = _first_conn[e->eindex()][isoutput];    while (c >= 0) {	int p = _conn[c].port(isoutput);	if (p >= v.size())	    v.resize(p + 1, -1);	if (v[p] >= 0)	    v[p] = -2;	else	    v[p] = c;	c = _conn[c].next(isoutput);    }}boolRouterT::insert_before(const PortT &inserter, const PortT &h){    if (!add_connection(inserter, h))	return false;    int i = _first_conn[h.eindex()][end_to];    while (i >= 0) {	int next = _conn[i].next_to();	if (_conn[i].to() == h && connection_live(i)	    && _conn[i].from() != inserter)	    change_connection_to(i, inserter);	i = next;    }    return true;}boolRouterT::insert_after(const PortT &inserter, const PortT &h){    if (!add_connection(h, inserter))	return false;    int i = _first_conn[h.eindex()][end_from];    while (i >= 0) {	int next = _conn[i].next_from();	if (_conn[i].from() == h && _conn[i].to() != inserter)	    change_connection_from(i, inserter);	i = next;    }    return true;}voidRouterT::add_tunnel(const String &namein, const String &nameout,		    const LandmarkT &landmark, ErrorHandler *errh){    if (!errh)	errh = ErrorHandler::silent_handler();    ElementClassT *tun = ElementClassT::tunnel_type();    ElementT *ein = get_element(namein, tun, String(), landmark);    ElementT *eout = get_element(nameout, tun, String(), landmark);    bool ok = true;    if (!ein->tunnel()) {	ElementT::redeclaration_error(errh, "element", namein, landmark, ein->landmark());	ok = false;    }    if (!eout->tunnel()) {	ElementT::redeclaration_error(errh, "element", nameout, landmark, eout->landmark());	ok = false;    }    if (ein->tunnel_output()) {	ElementT::redeclaration_error(errh, "connection tunnel input", namein, landmark, ein->landmark());	ok = false;    }    if (eout->tunnel_input()) {	ElementT::redeclaration_error(errh, "connection tunnel output", nameout, landmark, eout->landmark());	ok = false;    }    if (ok) {	ein->_tunnel_output = eout;	eout->_tunnel_input = ein;    }}//// REQUIREMENTS//voidRouterT::add_requirement(const String &s){    _requirements.push_back(s);}voidRouterT::remove_requirement(const String &s){    for (int i = 0; i < _requirements.size(); i++)	if (_requirements[i] == s) {	    // keep requirements in order	    for (int j = i + 1; j < _requirements.size(); j++)		_requirements[j-1] = _requirements[j];	    _requirements.pop_back();	    return;	}}voidRouterT::add_archive(const ArchiveElement &ae){    int &i = _archive_map[ae.name];    if (i >= 0)	_archive[i] = ae;    else {	i = _archive.size();	_archive.push_back(ae);    }}voidRouterT::remove_duplicate_connections(){    // 5.Dec.1999 - This function dominated the running time of click-xform.    // Use an algorithm faster on the common case (few connections per    // element).    int nelem = _elements.size();    Vector<int> removers;    for (int i = 0; i < nelem; i++) {	int trav = _first_conn[i][end_from];	int next = 0;		// initialize here to avoid gcc warnings	while (trav >= 0) {	    int prev = _first_conn[i][end_from];	    int trav_port = _conn[trav].from().port;	    next = _conn[trav].next_from();	    while (prev >= 0 && prev != trav) {		if (_conn[prev].from().port == trav_port		    && _conn[prev].to() == _conn[trav].to()) {		    kill_connection(conn_iterator(&_conn[trav], 0));		    goto duplicate;		}		prev = _conn[prev].next_from();	    }	  duplicate:	    trav = next;	}    }}voidRouterT::remove_dead_elements(ErrorHandler *errh){    if (!errh)	errh = ErrorHandler::silent_handler();    int nelements = _elements.size();    // change hookup    kill_bad_connections();    // find new element indexes    Vector<int> new_eindex(nelements, 0);    int j = 0;    for (int i = 0; i < nelements; i++)	if (_elements[i]->dead())	    new_eindex[i] = -1;	else	    new_eindex[i] = j++;    int new_nelements = j;    // compress element arrays    for (int i = 0; i < nelements; i++) {	j = new_eindex[i];	if (j < 0) {	    _element_name_map.set(_elements[i]->name(), -1);	    delete _elements[i];	} else if (j != i) {	    _element_name_map.set(_elements[i]->name(), j);	    _elements[j] = _elements[i];	    _elements[j]->_eindex = j;	    _first_conn[j] = _first_conn[i];	}    }    // resize element arrays    _elements.resize(new_nelements);    _first_conn.resize(new_nelements);    _n_live_elements = new_nelements;    _free_element = 0;}voidRouterT::free_element(ElementT *e){    assert(e->router() == this);    int ei = e->eindex();    // first, remove bad connections from other elements' connection lists    Vector<int> bad_from, bad_to;    for (int c = _first_conn[ei][end_from]; c >= 0; c = _conn[c].next_from())	unlink_connection_to(c);    for (int c = _first_conn[ei][end_to]; c >= 0; c = _conn[c].next_to())	unlink_connection_from(c);    // now, free all of this element's connections    for (int c = _first_conn[ei][end_from]; c >= 0; ) {	int next = _conn[c].next_from();	if (_conn[c].to_eindex() != ei)	    free_connection(c);	c = next;    }    for (int c = _first_conn[ei][end_to]; c >= 0; ) {	int next = _conn[c].next_to();	free_connection(c);	c = next;    }    _first_conn[ei] = Pair(-1, -1);    // finally, free the element itself    if (_element_name_map[e->name()] == ei)	_element_name_map.set(e->name(), -1);    e->simple_kill();    e->_tunnel_input = _free_element;    _free_element = e;    _n_live_elements--;    check();}voidRouterT::free_dead_elements(){    int nelements = _elements.size();    Vector<int> new_eindex(nelements, 0);    // mark saved findexes    for (int i = 0; i < nelements; i++)	if (_elements[i]->dead())	    new_eindex[i] = -1;    // don't free elements that have already been freed!!    for (ElementT *e = _free_element; e; e = e->tunnel_input())	new_eindex[e->eindex()] = 0;    // get rid of connections to and from dead elements    kill_bad_connections();

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -