Home | History | Annotate | Download | only in BsdSocketLib
      1 /*
      2  * Copyright (c) 1996 by Internet Software Consortium.
      3  *
      4  * Permission to use, copy, modify, and distribute this software for any
      5  * purpose with or without fee is hereby granted, provided that the above
      6  * copyright notice and this permission notice appear in all copies.
      7  *
      8  * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM DISCLAIMS
      9  * ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES
     10  * OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE
     11  * CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
     12  * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
     13  * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
     14  * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
     15  * SOFTWARE.
     16  */
     17 
     18 /*
     19  * Portions copyright (c) 1999, 2000
     20  * Intel Corporation.
     21  * All rights reserved.
     22  *
     23  * Redistribution and use in source and binary forms, with or without
     24  * modification, are permitted provided that the following conditions
     25  * are met:
     26  *
     27  * 1. Redistributions of source code must retain the above copyright
     28  *    notice, this list of conditions and the following disclaimer.
     29  *
     30  * 2. Redistributions in binary form must reproduce the above copyright
     31  *    notice, this list of conditions and the following disclaimer in the
     32  *    documentation and/or other materials provided with the distribution.
     33  *
     34  * 3. All advertising materials mentioning features or use of this software
     35  *    must display the following acknowledgement:
     36  *
     37  *    This product includes software developed by Intel Corporation and
     38  *    its contributors.
     39  *
     40  * 4. Neither the name of Intel Corporation or its contributors may be
     41  *    used to endorse or promote products derived from this software
     42  *    without specific prior written permission.
     43  *
     44  * THIS SOFTWARE IS PROVIDED BY INTEL CORPORATION AND CONTRIBUTORS ``AS IS''
     45  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     46  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     47  * ARE DISCLAIMED.  IN NO EVENT SHALL INTEL CORPORATION OR CONTRIBUTORS BE
     48  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     49  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     50  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     51  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     52  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     53  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
     54  * THE POSSIBILITY OF SUCH DAMAGE.
     55  *
     56  */
     57 
     58 /* Import. */
     59 
     60 #include <arpa/nameser.h>
     61 
     62 #include <ctype.h>
     63 #include <errno.h>
     64 #include <stdio.h>
     65 #include <string.h>
     66 
     67 #define SPRINTF(x) ((size_t)sprintf x)
     68 
     69 /* Forward. */
     70 
     71 static int	fmt1(int t, char s, char **buf, size_t *buflen);
     72 
     73 /* Macros. */
     74 
     75 #define T(x) if ((x) < 0) return (-1); else (void)NULL
     76 
     77 /* Public. */
     78 
     79 int
     80 ns_format_ttl(u_long src, char *dst, size_t dstlen) {
     81 	char *odst = dst;
     82 	int secs, mins, hours, days, weeks, x;
     83 	char *p;
     84 
     85 	secs =  (int)(src % 60);  src /= 60;
     86 	mins =  (int)(src % 60);  src /= 60;
     87 	hours = (int)(src % 24);  src /= 24;
     88 	days =  (int)(src % 7);   src /= 7;
     89 	weeks = (int)src;         src = 0;
     90 
     91 	x = 0;
     92 	if (weeks) {
     93 		T(fmt1(weeks, 'W', &dst, &dstlen));
     94 		x++;
     95 	}
     96 	if (days) {
     97 		T(fmt1(days, 'D', &dst, &dstlen));
     98 		x++;
     99 	}
    100 	if (hours) {
    101 		T(fmt1(hours, 'H', &dst, &dstlen));
    102 		x++;
    103 	}
    104 	if (mins) {
    105 		T(fmt1(mins, 'M', &dst, &dstlen));
    106 		x++;
    107 	}
    108 	if (secs || !(weeks || days || hours || mins)) {
    109 		T(fmt1(secs, 'S', &dst, &dstlen));
    110 		x++;
    111 	}
    112 
    113 	if (x > 1) {
    114 		int ch;
    115 
    116 		for (p = odst; (ch = *p) != '\0'; p++)
    117 			if (isascii(ch) && isupper(ch))
    118 				*p = (char)( tolower(ch));
    119 	}
    120 
    121 	return ((int)(dst - odst));
    122 }
    123 
    124 int
    125 ns_parse_ttl(const char *src, u_long *dst) {
    126 	u_long ttl, tmp;
    127 	int ch, digits, dirty;
    128 
    129 	ttl = 0;
    130 	tmp = 0;
    131 	digits = 0;
    132 	dirty = 0;
    133 	while ((ch = *src++) != '\0') {
    134 		if (!isascii(ch) || !isprint(ch))
    135 			goto einval;
    136 		if (isdigit(ch)) {
    137 			tmp *= 10;
    138 			tmp += (ch - '0');
    139 			digits++;
    140 			continue;
    141 		}
    142 		if (digits == 0)
    143 			goto einval;
    144 		if (islower(ch))
    145 			ch = toupper(ch);
    146 		switch (ch) {
    147 		case 'W':  tmp *= 7;
    148 		case 'D':  tmp *= 24;
    149 		case 'H':  tmp *= 60;
    150 		case 'M':  tmp *= 60;
    151 		case 'S':  break;
    152 		default:   goto einval;
    153 		}
    154 		ttl += tmp;
    155 		tmp = 0;
    156 		digits = 0;
    157 		dirty = 1;
    158 	}
    159 	if (digits > 0) {
    160 		if (dirty)
    161 			goto einval;
    162 		else
    163 			ttl += tmp;
    164 	}
    165 	*dst = ttl;
    166 	return (0);
    167 
    168  einval:
    169 	errno = EINVAL;
    170 	return (-1);
    171 }
    172 
    173 /* Private. */
    174 
    175 static int
    176 fmt1(int t, char s, char **buf, size_t *buflen) {
    177 	char tmp[50];
    178 	size_t len;
    179 
    180 	len = SPRINTF((tmp, "%d%c", t, s));
    181 	if (len + 1 > *buflen)
    182 		return (-1);
    183 	strcpy(*buf, tmp);
    184 	*buf += len;
    185 	*buflen -= len;
    186 	return (0);
    187 }
    188