mirror of
https://gitlab.isc.org/isc-projects/dhcp
synced 2025-08-22 09:57:20 +00:00
Fixes to lease input and output.
[ISC-Bugs #20418] - Some systems don't support the "%s" argument to strftime, paste together the same string using mktime instead. [ISC-Bugs #19596] - When parsing iaid values accept printable characters. [ISC-Bugs #21585] - Always print time values in omshell as hex instead of ascii if the values happen to be printable characters.
This commit is contained in:
parent
83d409ae59
commit
6aaaf6a460
8
RELNOTES
8
RELNOTES
@ -107,6 +107,14 @@ work on other platforms. Please report any problems and suggested fixes to
|
||||
date strings correctly. Thanks to a patch from Jiri Popelka at Red Hat.
|
||||
[ISC-Bugs #21501, #20598]
|
||||
|
||||
- Fixes to lease input and output.
|
||||
[ISC-Bugs #20418] - Some systems don't support the "%s" argument to
|
||||
strftime, paste together the same string using mktime instead.
|
||||
[ISC-Bugs #19596] - When parsing iaid values accept printable
|
||||
characters.
|
||||
[ISC-Bugs #21585] - Always print time values in omshell as hex
|
||||
instead of ascii if the values happen to be printable characters.
|
||||
|
||||
Changes since 4.2.0b2
|
||||
|
||||
- Add declaration for variable in debug code in alloc.c. [ISC-Bugs #21472]
|
||||
|
@ -3,7 +3,7 @@
|
||||
Parser for dhclient config and lease files... */
|
||||
|
||||
/*
|
||||
* Copyright (c) 2004-2009 by Internet Systems Consortium, Inc. ("ISC")
|
||||
* Copyright (c) 2004-2010 by Internet Systems Consortium, Inc. ("ISC")
|
||||
* Copyright (c) 1996-2003 by Internet Software Consortium
|
||||
*
|
||||
* Permission to use, copy, modify, and distribute this software for any
|
||||
@ -1521,12 +1521,12 @@ parse_client6_lease_statement(struct parse *cfile)
|
||||
static struct dhc6_ia *
|
||||
parse_client6_ia_na_statement(struct parse *cfile)
|
||||
{
|
||||
struct data_string id;
|
||||
struct option_cache *oc = NULL;
|
||||
struct dhc6_ia *ia;
|
||||
struct dhc6_addr **addr;
|
||||
const char *val;
|
||||
int token, no_semi;
|
||||
int token, no_semi, len;
|
||||
u_int8_t buf[5];
|
||||
|
||||
ia = dmalloc(sizeof(*ia), MDL);
|
||||
if (ia == NULL) {
|
||||
@ -1537,20 +1537,11 @@ parse_client6_ia_na_statement(struct parse *cfile)
|
||||
ia->ia_type = D6O_IA_NA;
|
||||
|
||||
/* Get IAID. */
|
||||
memset(&id, 0, sizeof(id));
|
||||
if (parse_cshl(&id, cfile)) {
|
||||
if (id.len == 4)
|
||||
memcpy(ia->iaid, id.data, 4);
|
||||
else {
|
||||
parse_warn(cfile, "Expecting IAID of length 4, got %d.",
|
||||
id.len);
|
||||
skip_to_semi(cfile);
|
||||
dfree(ia, MDL);
|
||||
return NULL;
|
||||
}
|
||||
data_string_forget(&id, MDL);
|
||||
len = parse_X(cfile, buf, 5);
|
||||
if (len == 4) {
|
||||
memcpy(ia->iaid, buf, 4);
|
||||
} else {
|
||||
parse_warn(cfile, "Expecting IAID.");
|
||||
parse_warn(cfile, "Expecting IAID of length 4, got %d.", len);
|
||||
skip_to_semi(cfile);
|
||||
dfree(ia, MDL);
|
||||
return NULL;
|
||||
@ -1658,12 +1649,12 @@ parse_client6_ia_na_statement(struct parse *cfile)
|
||||
static struct dhc6_ia *
|
||||
parse_client6_ia_ta_statement(struct parse *cfile)
|
||||
{
|
||||
struct data_string id;
|
||||
struct option_cache *oc = NULL;
|
||||
struct dhc6_ia *ia;
|
||||
struct dhc6_addr **addr;
|
||||
const char *val;
|
||||
int token, no_semi;
|
||||
int token, no_semi, len;
|
||||
u_int8_t buf[5];
|
||||
|
||||
ia = dmalloc(sizeof(*ia), MDL);
|
||||
if (ia == NULL) {
|
||||
@ -1674,20 +1665,11 @@ parse_client6_ia_ta_statement(struct parse *cfile)
|
||||
ia->ia_type = D6O_IA_TA;
|
||||
|
||||
/* Get IAID. */
|
||||
memset(&id, 0, sizeof(id));
|
||||
if (parse_cshl(&id, cfile)) {
|
||||
if (id.len == 4)
|
||||
memcpy(ia->iaid, id.data, 4);
|
||||
else {
|
||||
parse_warn(cfile, "Expecting IAID of length 4, got %d.",
|
||||
id.len);
|
||||
skip_to_semi(cfile);
|
||||
dfree(ia, MDL);
|
||||
return NULL;
|
||||
}
|
||||
data_string_forget(&id, MDL);
|
||||
len = parse_X(cfile, buf, 5);
|
||||
if (len == 4) {
|
||||
memcpy(ia->iaid, buf, 4);
|
||||
} else {
|
||||
parse_warn(cfile, "Expecting IAID.");
|
||||
parse_warn(cfile, "Expecting IAID of length 4, got %d.", len);
|
||||
skip_to_semi(cfile);
|
||||
dfree(ia, MDL);
|
||||
return NULL;
|
||||
@ -1775,12 +1757,12 @@ parse_client6_ia_ta_statement(struct parse *cfile)
|
||||
static struct dhc6_ia *
|
||||
parse_client6_ia_pd_statement(struct parse *cfile)
|
||||
{
|
||||
struct data_string id;
|
||||
struct option_cache *oc = NULL;
|
||||
struct dhc6_ia *ia;
|
||||
struct dhc6_addr **pref;
|
||||
const char *val;
|
||||
int token, no_semi;
|
||||
int token, no_semi, len;
|
||||
u_int8_t buf[5];
|
||||
|
||||
ia = dmalloc(sizeof(*ia), MDL);
|
||||
if (ia == NULL) {
|
||||
@ -1791,20 +1773,11 @@ parse_client6_ia_pd_statement(struct parse *cfile)
|
||||
ia->ia_type = D6O_IA_PD;
|
||||
|
||||
/* Get IAID. */
|
||||
memset(&id, 0, sizeof(id));
|
||||
if (parse_cshl(&id, cfile)) {
|
||||
if (id.len == 4)
|
||||
memcpy(ia->iaid, id.data, 4);
|
||||
else {
|
||||
parse_warn(cfile, "Expecting IAID of length 4, got %d.",
|
||||
id.len);
|
||||
skip_to_semi(cfile);
|
||||
dfree(ia, MDL);
|
||||
return NULL;
|
||||
}
|
||||
data_string_forget(&id, MDL);
|
||||
len = parse_X(cfile, buf, 5);
|
||||
if (len == 4) {
|
||||
memcpy(ia->iaid, buf, 4);
|
||||
} else {
|
||||
parse_warn(cfile, "Expecting IAID.");
|
||||
parse_warn(cfile, "Expecting IAID of length 4, got %d.", len);
|
||||
skip_to_semi(cfile);
|
||||
dfree(ia, MDL);
|
||||
return NULL;
|
||||
|
156
common/print.c
156
common/print.c
@ -358,44 +358,118 @@ void hash_dump (table)
|
||||
}
|
||||
}
|
||||
|
||||
#define HBLEN 60
|
||||
/*
|
||||
* print a string as hex. This only outputs
|
||||
* colon separated hex list no matter what
|
||||
* the input looks like. See print_hex
|
||||
* for a function that prints either cshl
|
||||
* or a string if all bytes are printible
|
||||
* It only uses limit characters from buf
|
||||
* and doesn't do anything if buf == NULL
|
||||
*
|
||||
* len - length of data
|
||||
* data - input data
|
||||
* limit - length of buf to use
|
||||
* buf - output buffer
|
||||
*/
|
||||
void print_hex_only (len, data, limit, buf)
|
||||
unsigned len;
|
||||
const u_int8_t *data;
|
||||
unsigned limit;
|
||||
char *buf;
|
||||
{
|
||||
unsigned i;
|
||||
|
||||
#define DECLARE_HEX_PRINTER(x) \
|
||||
char *print_hex##x (len, data, limit) \
|
||||
unsigned len; \
|
||||
const u_int8_t *data; \
|
||||
unsigned limit; \
|
||||
{ \
|
||||
\
|
||||
static char hex_buf##x [HBLEN + 1]; \
|
||||
unsigned i; \
|
||||
\
|
||||
if (limit > HBLEN) \
|
||||
limit = HBLEN; \
|
||||
\
|
||||
for (i = 0; i < (limit - 2) && i < len; i++) { \
|
||||
if (!isascii (data [i]) || !isprint (data [i])) { \
|
||||
for (i = 0; i < limit / 3 && i < len; i++) { \
|
||||
sprintf (&hex_buf##x [i * 3], \
|
||||
"%02x:", data [i]); \
|
||||
} \
|
||||
hex_buf##x [i * 3 - 1] = 0; \
|
||||
return hex_buf##x; \
|
||||
} \
|
||||
} \
|
||||
hex_buf##x [0] = '"'; \
|
||||
i = len; \
|
||||
if (i > limit - 2) \
|
||||
i = limit - 2; \
|
||||
memcpy (&hex_buf##x [1], data, i); \
|
||||
hex_buf##x [i + 1] = '"'; \
|
||||
hex_buf##x [i + 2] = 0; \
|
||||
return hex_buf##x; \
|
||||
if ((buf == NULL) || (limit < 3))
|
||||
return;
|
||||
|
||||
for (i = 0; (i < limit / 3) && (i < len); i++) {
|
||||
sprintf(&buf[i*3], "%02x:", data[i]);
|
||||
}
|
||||
buf[(i * 3) - 1] = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
DECLARE_HEX_PRINTER (_1)
|
||||
DECLARE_HEX_PRINTER (_2)
|
||||
DECLARE_HEX_PRINTER (_3)
|
||||
/*
|
||||
* print a string as either text if all the characters
|
||||
* are printable or colon separated hex if they aren't
|
||||
*
|
||||
* len - length of data
|
||||
* data - input data
|
||||
* limit - length of buf to use
|
||||
* buf - output buffer
|
||||
*/
|
||||
void print_hex_or_string (len, data, limit, buf)
|
||||
unsigned len;
|
||||
const u_int8_t *data;
|
||||
unsigned limit;
|
||||
char *buf;
|
||||
{
|
||||
unsigned i;
|
||||
if ((buf == NULL) || (limit < 3))
|
||||
return;
|
||||
|
||||
for (i = 0; (i < (limit - 3)) && (i < len); i++) {
|
||||
if (!isascii(data[i]) || !isprint(data[i])) {
|
||||
print_hex_only(len, data, limit, buf);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
buf[0] = '"';
|
||||
i = len;
|
||||
if (i > (limit - 3))
|
||||
i = limit - 3;
|
||||
memcpy(&buf[1], data, i);
|
||||
buf[i + 1] = '"';
|
||||
buf[i + 2] = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* print a string as either hex or text
|
||||
* using static buffers to hold the output
|
||||
*
|
||||
* len - length of data
|
||||
* data - input data
|
||||
* limit - length of buf
|
||||
* buf_num - the output buffer to use
|
||||
*/
|
||||
#define HBLEN 60
|
||||
char *print_hex(len, data, limit, buf_num)
|
||||
unsigned len;
|
||||
const u_int8_t *data;
|
||||
unsigned limit;
|
||||
unsigned buf_num;
|
||||
{
|
||||
static char hex_buf_1[HBLEN + 1];
|
||||
static char hex_buf_2[HBLEN + 1];
|
||||
static char hex_buf_3[HBLEN + 1];
|
||||
char *hex_buf;
|
||||
|
||||
switch(buf_num) {
|
||||
case 0:
|
||||
hex_buf = hex_buf_1;
|
||||
if (limit >= sizeof(hex_buf_1))
|
||||
limit = sizeof(hex_buf_1);
|
||||
break;
|
||||
case 1:
|
||||
hex_buf = hex_buf_2;
|
||||
if (limit >= sizeof(hex_buf_2))
|
||||
limit = sizeof(hex_buf_2);
|
||||
break;
|
||||
case 2:
|
||||
hex_buf = hex_buf_3;
|
||||
if (limit >= sizeof(hex_buf_3))
|
||||
limit = sizeof(hex_buf_3);
|
||||
break;
|
||||
default:
|
||||
return(NULL);
|
||||
}
|
||||
|
||||
print_hex_or_string(len, data, limit, hex_buf);
|
||||
return(hex_buf);
|
||||
}
|
||||
|
||||
#define DQLEN 80
|
||||
|
||||
@ -1391,6 +1465,8 @@ print_time(TIME t)
|
||||
{
|
||||
static char buf[sizeof("epoch 9223372036854775807; "
|
||||
"# Wed Jun 30 21:49:08 2147483647")];
|
||||
static char buf1[sizeof("# Wed Jun 30 21:49:08 2147483647")];
|
||||
time_t since_epoch;
|
||||
/* The string: "6 2147483647/12/31 23:59:60;"
|
||||
* is smaller than the other, used to declare the buffer size, so
|
||||
* we can use one buffer for both.
|
||||
@ -1412,10 +1488,14 @@ print_time(TIME t)
|
||||
#endif
|
||||
|
||||
if (db_time_format == LOCAL_TIME_FORMAT) {
|
||||
if (strftime(buf, sizeof(buf),
|
||||
"epoch %s; # %a %b %d %H:%M:%S %Y",
|
||||
localtime(&t)) == 0)
|
||||
since_epoch = mktime(localtime(&t));
|
||||
if ((strftime(buf1, sizeof(buf1),
|
||||
"# %a %b %d %H:%M:%S %Y",
|
||||
localtime(&t)) == 0) ||
|
||||
(snprintf(buf, sizeof(buf), "epoch %u; %s",
|
||||
since_epoch, buf1) >= sizeof(buf)))
|
||||
return NULL;
|
||||
|
||||
} else {
|
||||
/* No bounds check for the year is necessary - in this case,
|
||||
* strftime() will run out of space and assert an error.
|
||||
|
@ -3,7 +3,8 @@
|
||||
Examine and modify omapi objects. */
|
||||
|
||||
/*
|
||||
* Copyright (c) 2004-2007,2009 by Internet Systems Consortium, Inc. ("ISC")
|
||||
* Copyright (c) 2009-2010 by Internet Systems Consortium, Inc. ("ISC")
|
||||
* Copyright (c) 2004-2007 by Internet Systems Consortium, Inc. ("ISC")
|
||||
* Copyright (c) 2001-2003 by Internet Software Consortium
|
||||
*
|
||||
* Permission to use, copy, modify, and distribute this software for any
|
||||
@ -98,6 +99,7 @@ main(int argc, char **argv) {
|
||||
char buf[1024];
|
||||
char s1[1024];
|
||||
int connected = 0;
|
||||
char hex_buf[61];
|
||||
|
||||
for (i = 1; i < argc; i++) {
|
||||
usage(argv[0]);
|
||||
@ -159,10 +161,10 @@ main(int argc, char **argv) {
|
||||
break;
|
||||
|
||||
case omapi_datatype_data:
|
||||
printf ("%s\n",
|
||||
print_hex_1 (v -> value -> u.buffer.len,
|
||||
v -> value -> u.buffer.value,
|
||||
60));
|
||||
print_hex_only(v->value->u.buffer.len,
|
||||
v->value->u.buffer.value,
|
||||
sizeof(hex_buf), hex_buf);
|
||||
printf("%s\n", hex_buf);
|
||||
break;
|
||||
|
||||
case omapi_datatype_object:
|
||||
|
@ -2302,9 +2302,11 @@ void dump_packet_option (struct option_cache *, struct packet *,
|
||||
struct binding_scope **, struct universe *, void *);
|
||||
void dump_packet PROTO ((struct packet *));
|
||||
void hash_dump PROTO ((struct hash_table *));
|
||||
char *print_hex_1 PROTO ((unsigned, const u_int8_t *, unsigned));
|
||||
char *print_hex_2 PROTO ((unsigned, const u_int8_t *, unsigned));
|
||||
char *print_hex_3 PROTO ((unsigned, const u_int8_t *, unsigned));
|
||||
char *print_hex PROTO ((unsigned, const u_int8_t *, unsigned, unsigned));
|
||||
void print_hex_only PROTO ((unsigned, const u_int8_t *, unsigned, char *));
|
||||
#define print_hex_1(len, data, limit) print_hex(len, data, limit, 0)
|
||||
#define print_hex_2(len, data, limit) print_hex(len, data, limit, 1)
|
||||
#define print_hex_3(len, data, limit) print_hex(len, data, limit, 2)
|
||||
char *print_dotted_quads PROTO ((unsigned, const u_int8_t *));
|
||||
char *print_dec_1 PROTO ((unsigned long));
|
||||
char *print_dec_2 PROTO ((unsigned long));
|
||||
|
@ -3,7 +3,7 @@
|
||||
Persistent database management routines for DHCPD... */
|
||||
|
||||
/*
|
||||
* Copyright (c) 2004-2009 by Internet Systems Consortium, Inc. ("ISC")
|
||||
* Copyright (c) 2004-2010 by Internet Systems Consortium, Inc. ("ISC")
|
||||
* Copyright (c) 1995-2003 by Internet Software Consortium
|
||||
*
|
||||
* Permission to use, copy, modify, and distribute this software for any
|
||||
@ -594,11 +594,11 @@ write_ia(const struct ia_xx *ia) {
|
||||
binding_state) < 0) {
|
||||
goto error_exit;
|
||||
}
|
||||
if (fprintf(db_file, " preferred-life %u\n",
|
||||
if (fprintf(db_file, " preferred-life %u;\n",
|
||||
(unsigned)iasubopt->prefer) < 0) {
|
||||
goto error_exit;
|
||||
}
|
||||
if (fprintf(db_file, " max-life %u\n",
|
||||
if (fprintf(db_file, " max-life %u;\n",
|
||||
(unsigned)iasubopt->valid) < 0) {
|
||||
goto error_exit;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user