Skip to content

Commit 0d138d5

Browse files
committed
Fix propagation of implicit TTL
Use value specified in $TTL directive if available, use the last stated explicit TTL otherwise. Fixes NLnetLabs/nsd#375.
1 parent e72f29f commit 0d138d5

File tree

4 files changed

+22
-9
lines changed

4 files changed

+22
-9
lines changed

include/zone.h

+3-3
Original file line numberDiff line numberDiff line change
@@ -279,8 +279,6 @@ struct zone_rdata_buffer {
279279
*/
280280
#define ZONE_TAPE_SIZE ((100 * ZONE_BLOCK_SIZE) + ZONE_BLOCK_SIZE)
281281

282-
// @private
283-
284282
typedef struct zone_file zone_file_t;
285283
struct zone_file {
286284
/** @private */
@@ -290,7 +288,9 @@ struct zone_file {
290288
/** @private */
291289
uint16_t last_type;
292290
/** @private */
293-
uint32_t last_ttl, default_ttl;
291+
uint32_t last_ttl, dollar_ttl;
292+
/** @private */
293+
uint32_t *ttl, *default_ttl;
294294
/** @private */
295295
uint16_t last_class;
296296
/** Number of lines spanned by RR. */

src/generic/format.h

+7-4
Original file line numberDiff line numberDiff line change
@@ -161,11 +161,13 @@ static really_inline int32_t parse_rr(
161161

162162
int32_t code;
163163
const type_info_t *descriptor;
164+
const mnemonic_t *mnemonic;
164165
rdata_t rdata = { parser->rdata->octets, parser->rdata->octets + 65535 };
165166

166-
const mnemonic_t *mnemonic;
167+
parser->file->ttl = parser->file->default_ttl;
167168

168169
if ((uint8_t)token->data[0] - '0' < 10) {
170+
parser->file->ttl = &parser->file->last_ttl;
169171
if (!scan_ttl(token->data, token->length, parser->options.pretty_ttls, &parser->file->last_ttl))
170172
SYNTAX_ERROR(parser, "Invalid %s in %s", NAME(&fields[3]), NAME(&rr));
171173
if (parser->file->last_ttl & (1u << 31))
@@ -187,6 +189,7 @@ static really_inline int32_t parse_rr(
187189
if ((code = take_contiguous(parser, &rr, &fields[1], token)) < 0)
188190
return code;
189191
if ((uint8_t)token->data[0] - '0' < 10) {
192+
parser->file->ttl = &parser->file->last_ttl;
190193
if (!scan_ttl(token->data, token->length, parser->options.pretty_ttls, &parser->file->last_ttl))
191194
SYNTAX_ERROR(parser, "Invalid %s in %s", NAME(&fields[3]), NAME(&rr));
192195
if (parser->file->last_ttl & (1u << 31))
@@ -337,14 +340,14 @@ static really_inline int32_t parse_dollar_ttl(
337340

338341
if ((code = take_contiguous(parser, &ttl, &fields[0], token)) < 0)
339342
return code;
340-
if (!scan_ttl(token->data, token->length, parser->options.pretty_ttls, &parser->file->default_ttl))
343+
if (!scan_ttl(token->data, token->length, parser->options.pretty_ttls, &parser->file->dollar_ttl))
341344
SYNTAX_ERROR(parser, "Invalid %s in %s", NAME(&fields[0]), NAME(&ttl));
342-
if (parser->file->default_ttl & (1u << 31))
345+
if (parser->file->dollar_ttl & (1u << 31))
343346
SEMANTIC_ERROR(parser, "Invalid %s in %s", NAME(&fields[0]), NAME(&ttl));
344347
if ((code = take_delimiter(parser, &ttl, token)) < 0)
345348
return code;
346349

347-
parser->file->last_ttl = parser->file->default_ttl;
350+
parser->file->ttl = parser->file->default_ttl = &parser->file->dollar_ttl;
348351
adjust_line_count(parser->file);
349352
return 0;
350353
}

src/generic/types.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -216,7 +216,7 @@ static really_inline int32_t accept_rr(
216216
&(zone_name_t){ (uint8_t)parser->owner->length, parser->owner->octets },
217217
parser->file->last_type,
218218
parser->file->last_class,
219-
parser->file->last_ttl,
219+
*parser->file->ttl,
220220
(uint16_t)length,
221221
parser->rdata->octets,
222222
parser->user_data);

src/zone.c

+11-1
Original file line numberDiff line numberDiff line change
@@ -255,14 +255,24 @@ static void initialize_file(
255255
parser->options.origin.length);
256256
file->origin.length = parser->options.origin.length;
257257
file->last_class = parser->options.default_class;
258+
file->dollar_ttl = parser->options.default_ttl;
258259
file->last_ttl = parser->options.default_ttl;
260+
file->ttl = file->default_ttl = &file->last_ttl;
259261
} else {
260262
assert(parser->file);
261263
file->includer = parser->file;
262264
memcpy(&file->origin, &parser->file->origin, sizeof(file->origin));
263-
// retain class and TTL
265+
// Retain class and TTL values.
264266
file->last_class = parser->file->last_class;
267+
file->dollar_ttl = parser->file->dollar_ttl;
265268
file->last_ttl = parser->file->last_ttl;
269+
// RRs appearing after the $TTL directive that do not explicitly include
270+
// a TTL value, have their TTL set to the TTL in the $TTL directive. RRs
271+
// appearing before a $TTL directive use the last explicitly stated value.
272+
if (parser->file->default_ttl == &parser->file->last_ttl)
273+
file->ttl = file->default_ttl = &file->dollar_ttl;
274+
else
275+
file->ttl = file->default_ttl = &file->last_ttl;
266276
}
267277

268278
file->line = 1;

0 commit comments

Comments
 (0)