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

📄 ipripng_util.c

📁 这是最新的vxWorks6.7协议栈下的RIPng(rip over ipv6)实现
💻 C
📖 第 1 页 / 共 2 页
字号:
    p = ia->s6_addr;    for (i = 0; i < 16; i++) {        if (plen <= 0)            *p = 0;        else if (plen < 8)            *p &= plent[plen];        p++, plen -= 8;    }}/* * This function is required to add an offset to the time() call. * VxWorks returns time since bootup, but RIPng subtracts RIP_LIFETIME and * RIP_HOLDDOWN from this. If RIPng is started early after boot, then the * result of the subtraction is a negative number. Unfortunately time_t is an * unsigned long so the result is considered a high number in comparisons. * * The offset time returned from this ensures that time_t will never be * subtracted past zero. * * All calls to time() in this code are replaced by time_offset() calls. */IP_GLOBAL Ip_time_t time_offset(Ip_time_t *tod){    return (ipcom_time(tod) + RIP_LIFETIME + RIP_HOLDDOWN);}IP_GLOBAL Ip_time_t ipripng_nexttrigger_time(){    Ip_time_t t;    long r = ipcom_random();    t  = (int)(RIP_TRIG_INT6_MIN +        (RIP_TRIG_INT6_MAX - RIP_TRIG_INT6_MIN) * (r / IP_RAND_MAX ));    return t;}IP_GLOBAL intsin6mask2len(const struct Ip_sockaddr_in6 *sin6){	return mask2len(&sin6->sin6_addr,	    sin6->sin6_len - ip_offsetof(struct Ip_sockaddr_in6, sin6_addr));}IP_GLOBAL voidrtflags(struct  Ipnet_rt_msghdr *rtm,    char *ripng_rt_buf){    /*     * letter conflict should be okay.  painful when *BSD diverges...     */    ipcom_strcpy(ripng_rt_buf, "");#define RTFLAG(s, f) \do { \    if (rtm->rtm_flags & (f)) \        ipcom_strcat(ripng_rt_buf, (s));              \} while (0)    RTFLAG("U", IPNET_RTF_UP);    RTFLAG("G", IPNET_RTF_GATEWAY);    RTFLAG("H", IPNET_RTF_HOST);    RTFLAG("R", IPNET_RTF_REJECT);    RTFLAG("D", IPNET_RTF_DYNAMIC);    RTFLAG("M", IPNET_RTF_MODIFIED);    RTFLAG("d", IPNET_RTF_DONE);#ifdef  IPNET_RTF_MASK    RTFLAG("m", IPNET_RTF_MASK);#endif    RTFLAG("C", IPNET_RTF_CLONING);#ifdef IPNET_RTF_CLONED    RTFLAG("c", IPNET_RTF_CLONED);#endif#ifdef IPNET_RTF_PRCLONING    RTFLAG("c", IPNET_RTF_PRCLONING);#endif#ifdef IPNET_RTF_WASCLONED    RTFLAG("W", IPNET_RTF_WASCLONED);#endif    RTFLAG("X", IPNET_RTF_XRESOLVE);    RTFLAG("L", IPNET_RTF_LLINFO);    RTFLAG("S", IPNET_RTF_STATIC);    RTFLAG("B", IPNET_RTF_BLACKHOLE);#ifdef IPNET_RTF_PROTO3    RTFLAG("3", IPNET_RTF_PROTO3);#endif    RTFLAG("2", IPNET_RTF_PROTO2);    RTFLAG("1", IPNET_RTF_PROTO1);#ifdef IPNET_RTF_BROADCAST    RTFLAG("b", IPNET_RTF_BROADCAST);#endif#ifdef IPNET_RTF_DEFAULT    RTFLAG("d", IPNET_RTF_DEFAULT);#endif#ifdef IPNET_RTF_ISAROUTER    RTFLAG("r", IPNET_RTF_ISAROUTER);#endif#ifdef IPNET_RTF_TUNNEL    RTFLAG("T", IPNET_RTF_TUNNEL);#endif#ifdef IPNET_RTF_AUTH    RTFLAG("A", IPNET_RTF_AUTH);#endif#ifdef IPNET_RTF_CRYPT    RTFLAG("E", IPNET_RTF_CRYPT);#endif#undef RTFLAG}/* * outbound filter logic, per-route/interface. */IP_PUBLIC intout_filter(Ipripng_rt *rrt, struct ifc *ifcp){        struct iff *iffp;        struct in6_addr ia;        int ok;        /*         * -A: filter out less specific routes, if we have aggregated         * route configured.         */        for (iffp = ifcp->ifc_filter; iffp; iffp = iffp->iff_next) {                if (iffp->iff_type != 'A')                        continue;                if (rrt->rrt_info.rip6_plen <= iffp->iff_plen)                        continue;                ia = rrt->rrt_info.rip6_dest;                applyplen(&ia, iffp->iff_plen);                if (IP_IN6_ARE_ADDR_EQUAL(&ia, &iffp->iff_addr))                        return 0;        }        /*         * if it is an aggregated route, advertise it only to the         * interfaces specified on -A.         */        if ((rrt->rrt_rflags & RRTF_AGGREGATE) != 0) {                ok = 0;                for (iffp = ifcp->ifc_filter; iffp; iffp = iffp->iff_next) {                        if (iffp->iff_type != 'A')                                continue;                        if (rrt->rrt_info.rip6_plen == iffp->iff_plen &&                            IP_IN6_ARE_ADDR_EQUAL(&rrt->rrt_info.rip6_dest,                            &iffp->iff_addr)) {                                ok = 1;                                break;                        }                }                if (!ok)                        return 0;        }        /*         * -O: advertise only if prefix matches the configured prefix.         */        if (iff_find(ifcp, 'O')) {                ok = 0;                for (iffp = ifcp->ifc_filter; iffp; iffp = iffp->iff_next) {                        if (iffp->iff_type != 'O')                                continue;                        if (rrt->rrt_info.rip6_plen < iffp->iff_plen)                                continue;                        ia = rrt->rrt_info.rip6_dest;                        applyplen(&ia, iffp->iff_plen);                        if (IP_IN6_ARE_ADDR_EQUAL(&ia, &iffp->iff_addr)) {                                ok = 1;                                break;                        }                }                if (!ok)                        return 0;        }        /* the prefix should be advertised */        return 1;}/* * Determine if the route is to be advertised on the specified interface. * It checks options specified in the arguments and the split horizon rule. * Returns: *          0  - if the route shouldn't be advertised. *          1  - if route should be advertised. *          2  - if route should be advd with infinite hopcount (poison rev) * * RIPng-learned routes are advertised depending on -p/h/x/y/z settings * Static routes are advertised depending on the -s/S setting. * Interface routes are not advertised for poison reverse or split horizon. *  They are only advertised if Split Horizon is disabled. */IP_GLOBAL inttobeadv(Ipripng_rt *rrt, struct ifc *ifcp){    /* Special care for static routes */    if (rrt->rrt_flags & IPNET_RTF_STATIC) {        /* XXX don't advertise reject/blackhole routes */        if (rrt->rrt_flags & (IPNET_RTF_REJECT | IPNET_RTF_BLACKHOLE))            return 0;        if (ipripng_Sflag())    /* Yes, advertise it anyway */            return 1;        if (ipripng_sflag() && rrt->rrt_index != ifcp->ifc_index)            return 1;        return 0;    }    /* Split Horizon & Poison Reverse Config for this interface */    if (ifcp->ifc_horizcfg == IF_SPLITH && (rrt->rrt_index == ifcp->ifc_index))        return 0;    if (ifcp->ifc_horizcfg == IF_POISON && (rrt->rrt_index == ifcp->ifc_index))        {        /* If RIPng-learned, send route with metric 16. Otherwise don't send */        if (rrt->rrt_rflags & RRTF_RIPNGLEARNED)            return 2;        else            return 0;        }    return 1;}IP_GLOBAL Ip_boolipripng_neighbor_verify(struct in6_addr * nb_addr){    struct nb_list * plist = ipripng_nb_list_root();    struct in6_addr     noindex_addr;    while (plist)        {        struct in6_addr *   incoming_addr;        /* If link-local take the interface index out of the address */        if (IP_IN6_IS_ADDR_LINK_LOCAL(nb_addr))            {            noindex_addr = *nb_addr;            SET_IN6_LINKLOCAL_IFINDEX (noindex_addr, 0);            incoming_addr = &noindex_addr;            }        else            incoming_addr = nb_addr;        if (IP_IN6_ARE_ADDR_EQUAL(incoming_addr, &plist->nb_addr))            return (IP_TRUE);        plist = plist->nb_next;        }    /* None found */    return (IP_FALSE);}IP_STATIC const int pl2m[9] = {    0x00, 0x80, 0xc0, 0xe0, 0xf0, 0xf8, 0xfc, 0xfe, 0xff};IP_GLOBAL struct in6_addr *plen2mask(int n){    static struct in6_addr ia;    Ip_u8  *p;    int i;    memset(&ia, 0, sizeof(struct in6_addr));    p = (Ip_u8 *)&ia;    for (i = 0; i < 16; i++, p++, n -= 8) {        if (n >= 8) {            *p = 0xff;            continue;        }        *p = pl2m[n];        break;    }    return &ia;}/* **************************************************************************** *                      END OF FILE **************************************************************************** */

⌨️ 快捷键说明

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