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

📄 prnetdb.c

📁 Netscape NSPR库源码
💻 C
📖 第 1 页 / 共 4 页
字号:
            break;        case PR_IpAddrLoopback:            addr->inet.ip = htonl(INADDR_LOOPBACK);            break;        default:            PR_SetError(PR_INVALID_ARGUMENT_ERROR, 0);            rv = PR_FAILURE;        }    }    return rv;}  /* PR_SetNetAddr */PR_IMPLEMENT(PRBool)PR_IsNetAddrType(const PRNetAddr *addr, PRNetAddrValue val){    if (addr->raw.family == PR_AF_INET6) {        if (val == PR_IpAddrAny) {			if (_PR_IN6_IS_ADDR_UNSPECIFIED((PRIPv6Addr *)&addr->ipv6.ip)) {            	return PR_TRUE;			} else if (_PR_IN6_IS_ADDR_V4MAPPED((PRIPv6Addr *)&addr->ipv6.ip)					&& _PR_IN6_V4MAPPED_TO_IPADDR((PRIPv6Addr *)&addr->ipv6.ip)							== htonl(INADDR_ANY)) {            	return PR_TRUE;			}        } else if (val == PR_IpAddrLoopback) {            if (_PR_IN6_IS_ADDR_LOOPBACK((PRIPv6Addr *)&addr->ipv6.ip)) {            	return PR_TRUE;			} else if (_PR_IN6_IS_ADDR_V4MAPPED((PRIPv6Addr *)&addr->ipv6.ip)					&& _PR_IN6_V4MAPPED_TO_IPADDR((PRIPv6Addr *)&addr->ipv6.ip)							== htonl(INADDR_LOOPBACK)) {            	return PR_TRUE;			}        } else if (val == PR_IpAddrV4Mapped                && _PR_IN6_IS_ADDR_V4MAPPED((PRIPv6Addr *)&addr->ipv6.ip)) {            return PR_TRUE;        }    } else {        if (addr->raw.family == AF_INET) {            if (val == PR_IpAddrAny && addr->inet.ip == htonl(INADDR_ANY)) {                return PR_TRUE;            } else if (val == PR_IpAddrLoopback                    && addr->inet.ip == htonl(INADDR_LOOPBACK)) {                return PR_TRUE;            }        }    }    return PR_FALSE;}#ifndef _PR_INET6#define XX 127static const unsigned char index_hex[256] = {    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,     0, 1, 2, 3,  4, 5, 6, 7,  8, 9,XX,XX, XX,XX,XX,XX,    XX,10,11,12, 13,14,15,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,10,11,12, 13,14,15,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,    XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX,};/* * StringToV6Addr() returns 1 if the conversion succeeds, * or 0 if the input is not a valid IPv6 address string. * (Same as inet_pton(AF_INET6, string, addr).) */static int StringToV6Addr(const char *string, PRIPv6Addr *addr){    const unsigned char *s = (const unsigned char *)string;    int section = 0;        /* index of the current section (a 16-bit                             * piece of the address */    int double_colon = -1;  /* index of the section after the first                             * 16-bit group of zeros represented by                             * the double colon */    unsigned int val;    int len;    /* Handle initial (double) colon */    if (*s == ':') {        if (s[1] != ':') return 0;        s += 2;        addr->pr_s6_addr16[0] = 0;        section = double_colon = 1;    }    while (*s) {        if (section == 8) return 0; /* too long */        if (*s == ':') {            if (double_colon != -1) return 0; /* two double colons */            addr->pr_s6_addr16[section++] = 0;            double_colon = section;            s++;            continue;        }        for (len = val = 0; len < 4 && index_hex[*s] != XX; len++) {            val = (val << 4) + index_hex[*s++];        }        if (*s == '.') {            if (len == 0) return 0; /* nothing between : and . */            break;        }        if (*s == ':') {            s++;            if (!*s) return 0; /* cannot end with single colon */        } else if (*s) {            return 0; /* bad character */        }        addr->pr_s6_addr16[section++] = htons((unsigned short)val);    }        if (*s == '.') {        /* Have a trailing v4 format address */        if (section > 6) return 0; /* not enough room */        /*         * The number before the '.' is decimal, but we parsed it         * as hex.  That means it is in BCD.  Check it for validity         * and convert it to binary.         */        if (val > 0x0255 || (val & 0xf0) > 0x90 || (val & 0xf) > 9) return 0;        val = (val >> 8) * 100 + ((val >> 4) & 0xf) * 10 + (val & 0xf);        addr->pr_s6_addr[2 * section] = val;        s++;        val = index_hex[*s++];        if (val > 9) return 0;        while (*s >= '0' && *s <= '9') {            val = val * 10 + *s++ - '0';            if (val > 255) return 0;        }        if (*s != '.') return 0; /* must have exactly 4 decimal numbers */        addr->pr_s6_addr[2 * section + 1] = val;        section++;        s++;        val = index_hex[*s++];        if (val > 9) return 0;        while (*s >= '0' && *s <= '9') {            val = val * 10 + *s++ - '0';            if (val > 255) return 0;        }        if (*s != '.') return 0; /* must have exactly 4 decimal numbers */        addr->pr_s6_addr[2 * section] = val;        s++;        val = index_hex[*s++];        if (val > 9) return 0;        while (*s >= '0' && *s <= '9') {            val = val * 10 + *s++ - '0';            if (val > 255) return 0;        }        if (*s) return 0; /* must have exactly 4 decimal numbers */        addr->pr_s6_addr[2 * section + 1] = val;        section++;    }        if (double_colon != -1) {        /* Stretch the double colon */        int tosection;        int ncopy = section - double_colon;        for (tosection = 7; ncopy--; tosection--) {            addr->pr_s6_addr16[tosection] =                 addr->pr_s6_addr16[double_colon + ncopy];        }        while (tosection >= double_colon) {            addr->pr_s6_addr16[tosection--] = 0;        }    } else if (section != 8) {        return 0; /* too short */    }    return 1;}#undef XX            static const char *basis_hex = "0123456789abcdef";/* * V6AddrToString() returns a pointer to the buffer containing * the text string if the conversion succeeds, and NULL otherwise. * (Same as inet_ntop(AF_INET6, addr, buf, size), except that errno * is not set on failure.) */static const char *V6AddrToString(    const PRIPv6Addr *addr, char *buf, PRUint32 size){#define STUFF(c) do { \    if (!size--) return NULL; \    *buf++ = (c); \} while (0)    int double_colon = -1;          /* index of the first 16-bit                                     * group of zeros represented                                     * by the double colon */    int double_colon_length = 1;    /* use double colon only if                                     * there are two or more 16-bit                                     * groups of zeros */    int zero_length;    int section;    unsigned int val;    const char *bufcopy = buf;    /* Scan to find the placement of the double colon */    for (section = 0; section < 8; section++) {        if (addr->pr_s6_addr16[section] == 0) {            zero_length = 1;            section++;            while (section < 8 && addr->pr_s6_addr16[section] == 0) {                zero_length++;                section++;            }            /* Select the longest sequence of zeros */            if (zero_length > double_colon_length) {                double_colon = section - zero_length;                double_colon_length = zero_length;            }        }    }    /* Now start converting to a string */    section = 0;    if (double_colon == 0) {        if (double_colon_length == 6 ||            (double_colon_length == 5 && addr->pr_s6_addr16[5] == 0xffff)) {            /* ipv4 format address */            STUFF(':');            STUFF(':');            if (double_colon_length == 5) {                STUFF('f');                STUFF('f');                STUFF('f');                STUFF('f');                STUFF(':');            }            if (addr->pr_s6_addr[12] > 99) STUFF(addr->pr_s6_addr[12]/100 + '0');            if (addr->pr_s6_addr[12] > 9) STUFF((addr->pr_s6_addr[12]%100)/10 + '0');            STUFF(addr->pr_s6_addr[12]%10 + '0');            STUFF('.');            if (addr->pr_s6_addr[13] > 99) STUFF(addr->pr_s6_addr[13]/100 + '0');            if (addr->pr_s6_addr[13] > 9) STUFF((addr->pr_s6_addr[13]%100)/10 + '0');            STUFF(addr->pr_s6_addr[13]%10 + '0');            STUFF('.');            if (addr->pr_s6_addr[14] > 99) STUFF(addr->pr_s6_addr[14]/100 + '0');            if (addr->pr_s6_addr[14] > 9) STUFF((addr->pr_s6_addr[14]%100)/10 + '0');            STUFF(addr->pr_s6_addr[14]%10 + '0');            STUFF('.');            if (addr->pr_s6_addr[15] > 99) STUFF(addr->pr_s6_addr[15]/100 + '0');            if (addr->pr_s6_addr[15] > 9) STUFF((addr->pr_s6_addr[15]%100)/10 + '0');            STUFF(addr->pr_s6_addr[15]%10 + '0');            STUFF('\0');            return bufcopy;        }    }    while (section < 8) {        if (section == double_colon) {            STUFF(':');            STUFF(':');            section += double_colon_length;            continue;        }        val = ntohs(addr->pr_s6_addr16[section]);        if (val > 0xfff) {            STUFF(basis_hex[val >> 12]);        }        if (val > 0xff) {            STUFF(basis_hex[(val >> 8) & 0xf]);        }        if (val > 0xf) {            STUFF(basis_hex[(val >> 4) & 0xf]);        }        STUFF(basis_hex[val & 0xf]);        section++;        if (section < 8 && section != double_colon) STUFF(':');    }    STUFF('\0');    return bufcopy;#undef STUFF    }#endif /* !_PR_INET6 */PR_IMPLEMENT(PRStatus) PR_StringToNetAddr(const char *string, PRNetAddr *addr){    PRStatus status = PR_SUCCESS;    PRIntn rv;#if defined(_PR_INET6)    rv = inet_pton(AF_INET6, string, &addr->ipv6.ip);    if (1 == rv)    {        addr->raw.family = PR_AF_INET6;    }    else    {        PR_ASSERT(0 == rv);        /* clean up after the failed inet_pton() call */        memset(&addr->ipv6.ip, 0, sizeof(addr->ipv6.ip));        rv = inet_pton(AF_INET, string, &addr->inet.ip);        if (1 == rv)        {            addr->raw.family = AF_INET;        }        else        {            PR_ASSERT(0 == rv);            PR_SetError(PR_INVALID_ARGUMENT_ERROR, 0);            status = PR_FAILURE;        }    }#else /* _PR_INET6 */    rv = StringToV6Addr(string, &addr->ipv6.ip);    if (1 == rv) {        addr->raw.family = PR_AF_INET6;        return PR_SUCCESS;    }    PR_ASSERT(0 == rv);    /* clean up after the failed StringToV6Addr() call */    memset(&addr->ipv6.ip, 0, sizeof(addr->ipv6.ip));    addr->inet.family = AF_INET;#ifdef XP_OS2_VACPP    addr->inet.ip = inet_addr((char *)string);#else    addr->inet.ip = inet_addr(string);#endif    if ((PRUint32) -1 == addr->inet.ip)    {        /*         * The string argument is a malformed address string.         */        PR_SetError(PR_INVALID_ARGUMENT_ERROR, 0);        status = PR_FAILURE;    }#endif /* _PR_INET6 */    return status;}PR_IMPLEMENT(PRStatus) PR_NetAddrToString(    const PRNetAddr *addr, char *string, PRUint32 size){    if (PR_AF_INET6 == addr->raw.family)    {#if defined(_PR_INET6)        if (NULL == inet_ntop(AF_INET6, &addr->ipv6.ip, string, size))#else        if (NULL == V6AddrToString(&addr->ipv6.ip, string, size))#endif        {            /* the size of the result buffer is inadequate */            PR_SetError(PR_BUFFER_OVERFLOW_ERROR, 0);            return PR_FAILURE;        }    }    else    {        if (size < 16) goto failed;        if (AF_INET != addr->raw.family) goto failed;        else        {            unsigned char *byte = (unsigned char*)&addr->inet.ip;            PR_snprintf(string, size, "%u.%u.%u.%u",                byte[0], byte[1], byte[2], byte[3]);        }    }    return PR_SUCCESS;failed:    PR_SetError(PR_INVALID_ARGUMENT_ERROR, 0);    return PR_FAILURE;}  /* PR_NetAddrToString *//* * Convert an IPv4 addr to an (IPv4-mapped) IPv6 addr */PR_IMPLEMENT(void) PR_ConvertIPv4AddrToIPv6(PRUint32 v4addr, PRIPv6Addr *v6addr){    PRUint8 *dstp;    dstp = v6addr->pr_s6_addr;    memset(dstp, 0, 10);    memset(dstp + 10, 0xff, 2);    memcpy(dstp + 12,(char *) &v4addr, 4);}PR_IMPLEMENT(PRUint16) PR_ntohs(PRUint16 n) { return ntohs(n); }PR_IMPLEMENT(PRUint32) PR_ntohl(PRUint32 n) { return ntohl(n); }PR_IMPLEMENT(PRUint16) PR_htons(PRUint16 n) { return htons(n); }PR_IMPLEMENT(PRUint32) PR_htonl(PRUint32 n) { return htonl(n); }PR_IMPLEMENT(PRUint64) PR_ntohll(PRUint64 n){#ifdef IS_BIG_ENDIAN    return n;#else    PRUint64 tmp;    PRUint32 hi, lo;    LL_L2UI(lo, n);    LL_SHR(tmp, n, 32);    LL_L2UI(hi, tmp);    hi = PR_ntohl(hi);    lo = PR_ntohl(lo);    LL_UI2L(n, lo);    LL_SHL(n, n, 32);    LL_UI2L(tmp, hi);    LL_ADD(n, n, tmp);    return n;#endif}  /* ntohll */PR_IMPLEMENT(PRUint64) PR_htonll(PRUint64 n){#ifdef IS_BIG_ENDIAN    return n;#else    PRUint64 tmp;    PRUint32 hi, lo;    LL_L2UI(lo, n);    LL_SHR(tmp, n, 32);    LL_L2UI(hi, tmp);    hi = htonl(hi);    lo = htonl(lo);    LL_UI2L(n, lo);    LL_SHL(n, n, 32);    LL_UI2L(tmp, hi);    LL_ADD(n, n, tmp);    return n;#endif}  /* htonll */

⌨️ 快捷键说明

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