/* * NAME: conn->udp() * DESCRIPTION: set the challenge for attaching a UDP channel */ bool conn_udp(connection *conn, char *challenge, unsigned int len) { char buffer[UDPHASHSZ]; connection **hash; if (len == 0 || len > BINBUF_SIZE || conn->udpbuf != (char *) NULL) { return FALSE; /* invalid challenge */ } if (len >= UDPHASHSZ) { memcpy(buffer, challenge, UDPHASHSZ); } else { memset(buffer, '\0', UDPHASHSZ); memcpy(buffer, challenge, len); } hash = (connection **) ht_lookup(chtab, buffer, FALSE); while (*hash != (connection *) NULL && memcmp((*hash)->chain.name, buffer, UDPHASHSZ) == 0) { if ((*hash)->bufsz == len && memcmp((*hash)->udpbuf, challenge, len) == 0) { return FALSE; /* duplicate challenge */ } } conn->chain.next = (hte *) *hash; *hash = conn; conn->npkts = 0; m_static(); conn->udpbuf = ALLOC(char, BINBUF_SIZE); m_dynamic(); memset(conn->udpbuf, '\0', UDPHASHSZ); memcpy(conn->chain.name = conn->udpbuf, challenge, conn->bufsz = len); return TRUE; }
void test_blocks() { Matrix<int, M1+M2, N1+N2> m_fixed; MatrixXi m_dynamic(M1+M2, N1+N2); Matrix<int, M1, N1> mat11; mat11.setRandom(); Matrix<int, M1, N2> mat12; mat12.setRandom(); Matrix<int, M2, N1> mat21; mat21.setRandom(); Matrix<int, M2, N2> mat22; mat22.setRandom(); MatrixXi matx11 = mat11, matx12 = mat12, matx21 = mat21, matx22 = mat22; { VERIFY_IS_EQUAL((m_fixed << mat11, mat12, mat21, matx22).finished(), (m_dynamic << mat11, matx12, mat21, matx22).finished()); VERIFY_IS_EQUAL((m_fixed.template topLeftCorner<M1,N1>()), mat11); VERIFY_IS_EQUAL((m_fixed.template topRightCorner<M1,N2>()), mat12); VERIFY_IS_EQUAL((m_fixed.template bottomLeftCorner<M2,N1>()), mat21); VERIFY_IS_EQUAL((m_fixed.template bottomRightCorner<M2,N2>()), mat22); VERIFY_IS_EQUAL((m_fixed << mat12, mat11, matx21, mat22).finished(), (m_dynamic << mat12, matx11, matx21, mat22).finished()); } if(N1 > 0) { VERIFY_RAISES_ASSERT((m_fixed << mat11, mat12, mat11, mat21, mat22)); VERIFY_RAISES_ASSERT((m_fixed << mat11, mat12, mat21, mat21, mat22)); } else { // allow insertion of zero-column blocks: VERIFY_IS_EQUAL((m_fixed << mat11, mat12, mat11, mat11, mat21, mat21, mat22).finished(), (m_dynamic << mat12, mat22).finished()); } if(M1 != M2) { VERIFY_RAISES_ASSERT((m_fixed << mat11, mat21, mat12, mat22)); } }
void NETLIB_NAME(solver)::post_start() { std::vector<analog_net_t::list_t> groups; const bool use_specific = true; m_params.m_pivot = m_pivot(); m_params.m_accuracy = m_accuracy(); /* FIXME: Throw when negative */ m_params.m_gs_loops = static_cast<unsigned>(m_gs_loops()); m_params.m_nr_loops = static_cast<unsigned>(m_nr_loops()); m_params.m_nt_sync_delay = netlist_time::from_double(m_sync_delay()); m_params.m_lte = m_lte(); m_params.m_sor = m_sor(); m_params.m_min_timestep = m_min_timestep(); m_params.m_dynamic = (m_dynamic() == 1 ? true : false); m_params.m_max_timestep = netlist_time::from_double(1.0 / m_freq()).as_double(); if (m_params.m_dynamic) { m_params.m_max_timestep *= 1;//NL_FCONST(1000.0); } else { m_params.m_min_timestep = m_params.m_max_timestep; } //m_params.m_max_timestep = std::max(m_params.m_max_timestep, m_params.m_max_timestep::) // Override log statistics pstring p = plib::util::environment("NL_STATS"); if (p != "") m_params.m_log_stats = p.as_long(); else m_params.m_log_stats = m_log_stats(); netlist().log().verbose("Scanning net groups ..."); // determine net groups for (auto & net : netlist().m_nets) { netlist().log().debug("processing {1}\n", net->name()); if (!net->isRailNet()) { netlist().log().debug(" ==> not a rail net\n"); /* Must be an analog net */ analog_net_t *n = static_cast<analog_net_t *>(net.get()); if (!n->already_processed(groups)) { groups.push_back(analog_net_t::list_t()); n->process_net(groups); } } } // setup the solvers netlist().log().verbose("Found {1} net groups in {2} nets\n", groups.size(), netlist().m_nets.size()); for (auto & grp : groups) { std::unique_ptr<matrix_solver_t> ms; unsigned net_count = static_cast<unsigned>(grp.size()); switch (net_count) { case 1: ms = create_solver<1,1>(1, use_specific); break; case 2: ms = create_solver<2,2>(2, use_specific); break; case 3: ms = create_solver<3,3>(3, use_specific); break; case 4: ms = create_solver<4,4>(4, use_specific); break; case 5: ms = create_solver<5,5>(5, use_specific); break; case 6: ms = create_solver<6,6>(6, use_specific); break; case 7: ms = create_solver<7,7>(7, use_specific); break; case 8: ms = create_solver<8,8>(8, use_specific); break; case 10: ms = create_solver<10,10>(10, use_specific); break; case 11: ms = create_solver<11,11>(11, use_specific); break; case 12: ms = create_solver<12,12>(12, use_specific); break; case 15: ms = create_solver<15,15>(15, use_specific); break; case 31: ms = create_solver<31,31>(31, use_specific); break; case 49: ms = create_solver<49,49>(49, use_specific); break; #if 0 case 87: ms = create_solver<87,87>(87, use_specific); break; #endif default: netlist().log().warning("No specific solver found for netlist of size {1}", net_count); if (net_count <= 16) { ms = create_solver<0,16>(net_count, use_specific); } else if (net_count <= 32) { ms = create_solver<0,32>(net_count, use_specific); } else if (net_count <= 64) { ms = create_solver<0,64>(net_count, use_specific); } else if (net_count <= 128) { ms = create_solver<0,128>(net_count, use_specific); } else { netlist().log().fatal("Encountered netgroup with > 128 nets"); ms = nullptr; /* tease compilers */ } break; } // FIXME ... ms->set_delegate_pointer(); ms->setup(grp); netlist().log().verbose("Solver {1}", ms->name()); netlist().log().verbose(" ==> {2} nets", grp.size()); netlist().log().verbose(" has {1} elements", ms->has_dynamic_devices() ? "dynamic" : "no dynamic"); netlist().log().verbose(" has {1} elements", ms->has_timestep_devices() ? "timestep" : "no timestep"); for (auto &n : grp) { netlist().log().verbose("Net {1}", n->name()); for (const auto &pcore : n->m_core_terms) { netlist().log().verbose(" {1}", pcore->name()); } } m_mat_solvers.push_back(std::move(ms)); } }
/* * NAME: ipaddr->new() * DESCRIPTION: return a new ipaddr */ static ipaddr *ipa_new(in46addr *ipnum) { ipaddr *ipa, **hash; /* check hash table */ # ifdef INET6 if (ipnum->ipv6) { hash = &ipahtab[hashmem((char *) ipnum, sizeof(struct in6_addr)) % ipahtabsz]; } else # endif { hash = &ipahtab[(Uint) ipnum->in.addr.s_addr % ipahtabsz]; } while (*hash != (ipaddr *) NULL) { ipa = *hash; # ifdef INET6 if (ipnum->ipv6 == ipa->ipnum.ipv6 && ((ipnum->ipv6) ? memcmp(&ipnum->in.addr6, &ipa->ipnum.in.addr6, sizeof(struct in6_addr)) == 0 : ipnum->in.addr.s_addr == ipa->ipnum.in.addr.s_addr)) { # else if (ipnum->in.addr.s_addr == ipa->ipnum.in.addr.s_addr) { # endif /* * found it */ if (ipa->ref == 0) { /* remove from free list */ if (ipa->prev == (ipaddr *) NULL) { ffirst = ipa->next; } else { ipa->prev->next = ipa->next; } if (ipa->next == (ipaddr *) NULL) { flast = ipa->prev; } else { ipa->next->prev = ipa->prev; } ipa->prev = ipa->next = (ipaddr *) NULL; --nfree; } ipa->ref++; if (ipa->name[0] == '\0' && ipa != lastreq && ipa->prev == (ipaddr *) NULL && ipa != qhead) { if (!busy) { /* send query to name resolver */ write(out, (char *) ipnum, sizeof(in46addr)); lastreq = ipa; busy = TRUE; } else { /* put in request queue */ ipa->prev = qtail; if (qtail == (ipaddr *) NULL) { qhead = ipa; } else { qtail->next = ipa; } qtail = ipa; } } return ipa; } hash = &ipa->link; } if (nfree >= NFREE) { ipaddr **h; /* * use first ipaddr in free list */ ipa = ffirst; ffirst = ipa->next; ffirst->prev = (ipaddr *) NULL; --nfree; if (ipa == lastreq) { lastreq = (ipaddr *) NULL; } if (hash != &ipa->link) { /* remove from hash table */ # ifdef INET6 if (ipa->ipnum.ipv6) { h = &ipahtab[hashmem((char *) &ipa->ipnum, sizeof(struct in6_addr)) % ipahtabsz]; } else # endif { h = &ipahtab[(Uint) ipa->ipnum.in.addr.s_addr % ipahtabsz]; } while (*h != ipa) { h = &(*h)->link; } *h = ipa->link; /* put in hash table */ ipa->link = *hash; *hash = ipa; } } else { /* * allocate new ipaddr */ m_static(); ipa = ALLOC(ipaddr, 1); m_dynamic(); /* put in hash table */ ipa->link = *hash; *hash = ipa; } ipa->ref = 1; ipa->ipnum = *ipnum; ipa->name[0] = '\0'; ipa->prev = ipa->next = (ipaddr *) NULL; if (!busy) { /* send query to name resolver */ write(out, (char *) ipnum, sizeof(in46addr)); lastreq = ipa; busy = TRUE; } else { /* put in request queue */ ipa->prev = qtail; if (qtail == (ipaddr *) NULL) { qhead = ipa; } else { qtail->next = ipa; } qtail = ipa; } return ipa; } /* * NAME: ipaddr->del() * DESCRIPTION: delete an ipaddr */ static void ipa_del(ipaddr *ipa) { if (--ipa->ref == 0) { if (ipa->prev != (ipaddr *) NULL || qhead == ipa) { /* remove from queue */ if (ipa->prev != (ipaddr *) NULL) { ipa->prev->next = ipa->next; } else { qhead = ipa->next; } if (ipa->next != (ipaddr *) NULL) { ipa->next->prev = ipa->prev; } else { qtail = ipa->prev; } } /* add to free list */ if (flast != (ipaddr *) NULL) { flast->next = ipa; ipa->prev = flast; flast = ipa; } else { ffirst = flast = ipa; ipa->prev = (ipaddr *) NULL; } ipa->next = (ipaddr *) NULL; nfree++; } } /* * NAME: ipaddr->lookup() * DESCRIPTION: lookup another ip name */ static void ipa_lookup() { ipaddr *ipa; if (lastreq != (ipaddr *) NULL) { /* read ip name */ lastreq->name[read(in, lastreq->name, MAXHOSTNAMELEN)] = '\0'; } else { char buf[MAXHOSTNAMELEN]; /* discard ip name */ read(in, buf, MAXHOSTNAMELEN); } /* if request queue not empty, write new query */ if (qhead != (ipaddr *) NULL) { ipa = qhead; write(out, (char *) &ipa->ipnum, sizeof(in46addr)); qhead = ipa->next; if (qhead == (ipaddr *) NULL) { qtail = (ipaddr *) NULL; } else { qhead->prev = (ipaddr *) NULL; } ipa->prev = ipa->next = (ipaddr *) NULL; lastreq = ipa; busy = TRUE; } else { lastreq = (ipaddr *) NULL; busy = FALSE; } }