diff --git a/Doxyfile b/Doxyfile
index 54f6145e40b275f6757743306d1c1a67e3a80256..b0163856ae2cd3258b547ac4947dfc73d15d6eba 100644
--- a/Doxyfile
+++ b/Doxyfile
@@ -595,7 +595,6 @@ INPUT                  = src/common \
                          src/libknot \
                          src/common \
                          src/knot \
-                         src/zcompile \
                          src/zscanner \
                          src/utils \
                          Doxy.page.h
diff --git a/Knot.files b/Knot.files
index c74974e80ae149cfec0077ad5de2af3977cbbb08..56517c0314aba41d72beee8d7e8fd1c8d1ff0e4e 100644
--- a/Knot.files
+++ b/Knot.files
@@ -57,8 +57,6 @@ src/libknot/zone/zone-contents.c
 src/libknot/zone/zone-contents.h
 src/libknot/zone/zone-tree.h
 src/libknot/zone/zone-tree.c
-src/libknot/zone/dname-table.h
-src/libknot/zone/dname-table.c
 src/Makefile.am
 src/common/hattrie
 src/common/hattrie/ahtable.c
@@ -124,16 +122,6 @@ src/common/fdset_kqueue.h
 src/common/fdset_kqueue.c
 src/common/log.c
 src/common/log.h
-src/zcompile/parser-descriptor.h
-src/zcompile/parser-descriptor.c
-src/zcompile/parser-util.h
-src/zcompile/parser-util.c
-src/zcompile/zcompile.c
-src/zcompile/zcompile.h
-src/zcompile/zparser.y
-src/zcompile/zlexer.l
-src/zcompile/zcompile-error.h
-src/zcompile/zcompile_main.c
 src/knot/common.h
 src/knot/main.c
 src/knot/ctl/knotc_main.c
@@ -173,15 +161,10 @@ src/knot/conf/conf.c
 src/knot/conf/conf.h
 src/knot/conf/logconf.c
 src/knot/conf/logconf.h
-src/knot/zone/zone-dump.c
-src/knot/zone/zone-dump.h
 src/knot/zone/zone-load.c
 src/knot/zone/zone-load.h
 src/knot/zone/zone-dump-text.h
 src/knot/zone/zone-dump-text.c
-src/zcompile/tests/unittests_zp_main.c
-src/zcompile/tests/zcompile_tests.c
-src/zcompile/zcompile-error.c
 src/tests/unittests_main.c
 src/tests/common/acl_tests.c
 src/tests/common/acl_tests.h
@@ -206,55 +189,8 @@ src/tests/knot/journal_tests.h
 src/tests/knot/server_tests.c
 src/tests/knot/server_tests.h
 src/tests/libknot/unittests_libknot.c
-src/tests/libknot/libknot/dname_tests.c
-src/tests/libknot/libknot/dname_tests.h
-src/tests/libknot/libknot/edns_tests.c
-src/tests/libknot/libknot/edns_tests.h
-src/tests/libknot/libknot/node_tests.c
-src/tests/libknot/libknot/node_tests.h
-src/tests/libknot/libknot/rdata_tests.c
-src/tests/libknot/libknot/rdata_tests.h
-src/tests/libknot/libknot/response_tests.c
-src/tests/libknot/libknot/response_tests.h
 src/tests/libknot/libknot/rrset_tests.c
 src/tests/libknot/libknot/rrset_tests.h
-src/tests/libknot/libknot/zone_tests.c
-src/tests/libknot/libknot/zone_tests.h
-src/tests/libknot/libknot/zonedb_tests.c
-src/tests/libknot/libknot/zonedb_tests.h
-src/tests/libknot/libknot/cuckoo_tests.c
-src/tests/libknot/libknot/cuckoo_tests.h
-src/tests/libknot/libknot/dname_table_tests.h
-src/tests/libknot/libknot/dname_table_tests.c
-src/tests/libknot/libknot/packet_tests.c
-src/tests/libknot/libknot/packet_tests.h
-src/tests/libknot/libknot/query_tests.c
-src/tests/libknot/libknot/query_tests.h
-src/tests/libknot/libknot/nsec3_tests.c
-src/tests/libknot/libknot/nsec3_tests.h
-src/tests/libknot/realdata/unittests_libknot_realdata.c
-src/tests/libknot/realdata/libknot/packet_tests_realdata.c
-src/tests/libknot/realdata/libknot/packet_tests_realdata.h
-src/tests/libknot/realdata/libknot/dname_tests_realdata.c
-src/tests/libknot/realdata/libknot/dname_tests_realdata.h
-src/tests/libknot/realdata/libknot/edns_tests_realdata.c
-src/tests/libknot/realdata/libknot/edns_tests_realdata.h
-src/tests/libknot/realdata/libknot/node_tests_realdata.c
-src/tests/libknot/realdata/libknot/node_tests_realdata.h
-src/tests/libknot/realdata/libknot/rdata_tests_realdata.c
-src/tests/libknot/realdata/libknot/rdata_tests_realdata.h
-src/tests/libknot/realdata/libknot/response_tests_realdata.c
-src/tests/libknot/realdata/libknot/response_tests_realdata.h
-src/tests/libknot/realdata/libknot/rrset_tests_realdata.c
-src/tests/libknot/realdata/libknot/rrset_tests_realdata.h
-src/tests/libknot/realdata/libknot/zone_tests_realdata.c
-src/tests/libknot/realdata/libknot/zone_tests_realdata.h
-src/tests/libknot/realdata/libknot/zonedb_tests_realdata.c
-src/tests/libknot/realdata/libknot/zonedb_tests_realdata.h
-src/tests/libknot/realdata/libknot_tests_loader_realdata.c
-src/tests/libknot/realdata/libknot_tests_loader_realdata.h
-src/tests/libknot/libknot/zone_tree_tests.c
-src/tests/libknot/libknot/zone_tree_tests.h
 samples/Makefile.am
 src/libknot/tsig.h
 src/libknot/tsig.c
diff --git a/src/Makefile.am b/src/Makefile.am
index a05def8eb0ed7eac93c5df7866c6c242b32efda1..80c4557e24e4f5f2f6f08822d53aefdefb104e08 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -89,12 +89,8 @@ libknot_la_SOURCES =				\
 	libknot/zone/zonedb.c			\
 	libknot/zone/zonedb.h			\
 	libknot/zone/node.c			\
-	libknot/zone/dname-table.h		\
-	libknot/zone/dname-table.c		\
 	libknot/zone/zone-diff.h		\
 	libknot/zone/zone-diff.c		\
-	zcompile/zcompile.h			\
-	zcompile/zcompile.c			\
 	libknot/hash/hash-functions.c		\
 	libknot/hash/cuckoo-hash-table.c	\
 	libknot/hash/universal-system.c		\
@@ -225,6 +221,8 @@ libknotd_la_SOURCES =				\
 	knot/server/zones.h			\
 	knot/zone/semantic-check.c		\
 	knot/zone/semantic-check.h		\
+	knot/zone/zone-load.h			\
+	knot/zone/zone-load.c			\
 	knot/server/server.h
 
 zscanner/scanner.c: zscanner/scanner.rl zscanner/scanner_body.rl
diff --git a/src/knot/server/journal.c b/src/knot/server/journal.c
index faa911398acf395ec47e8b0be621415464a34eb9..f6f6072266153ad964fc90ce7d2fc6a23b52b567 100644
--- a/src/knot/server/journal.c
+++ b/src/knot/server/journal.c
@@ -24,8 +24,8 @@
 #include <sys/mman.h>
 
 #include "common/crc.h"
+#include "common.h"
 #include "knot/other/debug.h"
-#include "knot/zone/zone-dump.h"
 #include "journal.h"
 
 /*! \brief Infinite file size limit. */
diff --git a/src/knot/server/journal.h b/src/knot/server/journal.h
index 94628095e8f4edfdaa772e320704458f1aae533f..cd7377b54fb5e75673a391ad07c9a1e23a2ecb3c 100644
--- a/src/knot/server/journal.h
+++ b/src/knot/server/journal.h
@@ -44,6 +44,8 @@
 #include <stdint.h>
 #include <fcntl.h>
 
+#include "knot/zone/zone-load.h"
+
 /*!
  * \brief Journal entry flags.
  */
diff --git a/src/knot/server/zones.c b/src/knot/server/zones.c
index 4f7ecfb46ffe60e1d157fe766e733c80add173c2..4dfd9063265eaadc69de664ffd510ea0b23cbd9f 100644
--- a/src/knot/server/zones.c
+++ b/src/knot/server/zones.c
@@ -33,7 +33,6 @@
 #include "knot/server/xfr-handler.h"
 #include "libknot/updates/xfr-in.h"
 #include "knot/server/zones.h"
-#include "knot/zone/zone-dump.h"
 #include "libknot/nameserver/name-server.h"
 #include "libknot/updates/changesets.h"
 #include "libknot/tsig-op.h"
@@ -41,7 +40,6 @@
 #include "libknot/packet/response.h"
 #include "libknot/zone/zone-diff.h"
 #include "libknot/updates/ddns.h"
-#include "zcompile/zcompile.h"
 
 static const size_t XFRIN_CHANGESET_BINARY_SIZE = 100;
 static const size_t XFRIN_CHANGESET_BINARY_STEP = 100;
@@ -875,38 +873,19 @@ static int zones_load_zone(knot_zone_t **dst, const char *zone_name,
 	}
 	*dst = NULL;
 	
-	/* Duplicate zone name. */
-	size_t zlen = strlen(zone_name);
-	char *zname = NULL;
-	if (zlen > 0) {
-		if ((zname = strdup(zone_name)) == NULL) {
-			return KNOT_ENOMEM;
-		}
-	} else {
-		return KNOT_EINVAL;
-	}
-	zname[zlen - 1] = '\0'; /* Trim last dot */
-	
-	/* Check if the compiled file still exists. */
-	struct stat st;
-	if (stat(source, &st) != 0) {
-		char reason[256] = {0};
-		strerror_r(errno, reason, sizeof(reason));
-		log_server_warning("Failed to open zone file '%s' (%s).\n",
-		                   zname, reason);
-		free(zname);
-		return KNOT_EZONEINVAL;
-	}
-	
-	int ret = zone_read(zone_name, source, 0, dst);
-	/* Attempt to open compiled zone for loading. */
+	zloader_t *zl = NULL;
+	int ret = knot_zload_open(&zl, source, zone_name, 0);
 	if (ret != KNOT_EOK) {
-		log_server_warning("Failed to parser zone file '%s' (%s).\n",
-		                   source, knot_strerror(ret));
-		free(zname);
 		return ret;
 	}
 	
+	*dst = knot_zload_load(zl);
+	if (*dst == NULL) {
+		log_zone_error("Zone %s could not be loaded.\n", zone_name);
+		knot_zload_close(zl);
+		return KNOT_ERROR;
+	}
+	
 	//TODO, change to zone parsing
 //	switch(knot_zload_open(&zl, filename)) {
 //	case KNOT_EOK:
@@ -966,7 +945,7 @@ static int zones_load_zone(knot_zone_t **dst, const char *zone_name,
 	/* Check if loaded origin matches. */
 	const knot_dname_t *dname = knot_zone_name(*dst);
 	knot_dname_t *dname_req = NULL;
-	dname_req = knot_dname_new_from_str(zone_name, zlen, 0);
+	dname_req = knot_dname_new_from_str(zone_name, strlen(zone_name), 0);
 	if (knot_dname_compare(dname, dname_req) != 0) {
 		log_server_error("Origin of the zone db file is "
 				 "different than '%s'\n",
@@ -975,18 +954,17 @@ static int zones_load_zone(knot_zone_t **dst, const char *zone_name,
 		ret = KNOT_EZONEINVAL;
 	} else {
 		/* Save the timestamp from the zone db file. */
-		if (stat(source, &st) < 0) { // TODO REVIEW MV
-			dbg_zones("zones: failed to stat() zone db, "
-				  "something is seriously wrong\n");
-			knot_zone_deep_free(dst, 0);
-			ret = KNOT_EZONEINVAL;
-		} else {
-			knot_zone_set_version(*dst, st.st_mtime);
-		}
+//		if (stat(source, &st) < 0) { // TODO REVIEW MV
+//			dbg_zones("zones: failed to stat() zone db, "
+//				  "something is seriously wrong\n");
+//			knot_zone_deep_free(dst, 0);
+//			ret = KNOT_EZONEINVAL;
+//		} else {
+//			knot_zone_set_version(*dst, st.st_mtime);
+//		}
 	}
 	knot_dname_free(&dname_req);
-//	knot_zload_close(zl);
-	free(zname);
+	knot_zload_close(zl);
 	return ret;
 }
 
diff --git a/src/knot/zone/semantic-check.c b/src/knot/zone/semantic-check.c
index 32b21325ca782e72ff8347bb3601249bcfad3a4c..09d223528b81ceacb897c04dd8b911efa118a762 100644
--- a/src/knot/zone/semantic-check.c
+++ b/src/knot/zone/semantic-check.c
@@ -3,12 +3,12 @@
 #include <arpa/inet.h>
 
 #include "knot/common.h"
-#include "knot/zone/zone-dump.h"
 #include "knot/other/debug.h"
 #include "libknot/libknot.h"
 #include "common/base32hex.h"
 #include "common/crc.h"
 #include "common/descriptor_new.h"
+#include "common/mempattern.h"
 
 #include "semantic-check.h"
 
diff --git a/src/knot/zone/zone-dump.c b/src/knot/zone/zone-dump.c
deleted file mode 100644
index c24afb3724ef183f61f257a083e25ef7194ea2b8..0000000000000000000000000000000000000000
--- a/src/knot/zone/zone-dump.c
+++ /dev/null
@@ -1,1119 +0,0 @@
-/*  Copyright (C) 2011 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <config.h>
-#include <stdio.h>
-#include <stdint.h>
-#include <assert.h>
-#include <netinet/in.h>
-#include <unistd.h>
-#include <fcntl.h>
-#include <sys/stat.h>
-
-#include "libknot/common.h"
-#include "knot/zone/zone-dump.h"
-#include "libknot/libknot.h"
-#include "common/crc.h"
-#include "knot/other/debug.h"
-#include "common/skip-list.h"
-#include "semantic-check.h"
-
-/*! \note Contents of a dump file:
- * MAGIC(knotxx) db_filename dname_table
- * NUMBER_OF_NORMAL_NODES NUMBER_OF_NSEC3_NODES
- * [normal_nodes] [nsec3_nodes]
- * --------------------------------------------
- * dname_table is dumped as follows:
- * NUMBER_OF_DNAMES [dname_wire_length dname_wire label_count dname_labels ID]
- * node has following format:
- * owner_id
- * node_flags node_rrset_count [node_rrsets]
- * rrset has following format:
- * rrset_type rrset_class rrset_ttl rrset_rdata_count rrset_rrsig_count
- * [rrset_rdata] [rrset_rrsigs]
- * rdata can contain either dname ID,
- * or raw data stored like this: data_len [data]
- */
-
-static const size_t BUFFER_SIZE = 4096;
-
-static inline int write_to_file_crc(const void *src,
-                                     size_t size, size_t n, int fd,
-                                     crc_t *crc)
-{
-	if (src == NULL || fd < 0) {
-		return KNOT_EINVAL;
-	}
-	ssize_t rc = write(fd, src, size * n);
-	if (rc != size * n) {
-		fprintf(stderr, "write: invalid write %zd (expected %zu)\n", rc,
-			n);
-	}
-
-	if (size * n > 0) {
-		*crc =
-			crc_update(*crc, (unsigned char *)src,
-		                   size * n);
-	}
-
-	return rc == size * n;
-}
-
-static inline int write_to_stream(const void *src,
-                                  size_t size, size_t n,
-                                  uint8_t *stream,
-                                  size_t max_size,
-                                  size_t *written_bytes)
-{
-	if (src == NULL || stream == NULL || written_bytes == NULL) {
-		return KNOT_EINVAL;
-	}
-	
-	/* Check that the stream boundary will not be crossed. */
-	if (*written_bytes + (size * n) > max_size) {
-		/* Buffer overflown. */
-		dbg_zdump("zdump: write_to_stream: Cannot write to stream, no "
-		          "space left.\n");
-		return KNOT_ERANGE;
-	}
-	
-	/* Do the actual write. */
-	memcpy(stream + *written_bytes, src, size * n);
-	/* Expand size. */
-	*written_bytes += (size * n);
-	
-	return KNOT_EOK;
-}
-
-static int write_wrapper(const void *src,
-                         size_t size, size_t n, int fd,
-                         uint8_t *stream, size_t max_size,
-                         size_t *written_bytes, crc_t *crc)
-{
-	if (src == NULL) {
-		dbg_zdump("zdump: write_wrapper: NULL source.\n");
-		return KNOT_EINVAL;
-	}
-	
-	dbg_zdump_detail("zdump: write_wrapper: Writing %zu bytes to fd: %d.\n",
-	                 size * n, fd);
-	
-	if (fd < 0) {
-		assert(stream && written_bytes);
-		assert(crc == NULL);
-		/*!< \todo To comply with calling convention of write_wrapper,
-		 * we have to lose the error. */
-		int ret = write_to_stream(src, size, n, stream, max_size,
-		                          written_bytes);
-		if (ret != KNOT_EOK) {
-			dbg_zdump("zdump: write_wrapper: Could not write to "
-			          "stream. Reason: %s.\n", knot_strerror(ret));
-			/* Intentional! */
-			return 0;
-		} else {
-			/* Intentional! */
-			return 1;
-		}
-	} else {
-		/* Write to buffer first, if possible. */
-		if (*written_bytes + (size * n) < BUFFER_SIZE) {
-			dbg_zdump_detail("zdump: write_wrapper: Fits to "
-			                 "buffer. Remaining=%lu.\n",
-			                 BUFFER_SIZE - *written_bytes);
-			int ret = write_to_stream(src, size, n,
-			                          stream,
-			                          BUFFER_SIZE, written_bytes);
-			if (ret != KNOT_EOK) {
-				dbg_zdump("zdump: write_wrapper: "
-				          "Could not write to "
-				          "stream. Reason: %s.\n",
-				          knot_strerror(ret));
-				/* Intentional! */
-				return 0;
-			} else {
-				/* Intentional! */
-				return 1;
-			}
-		} else {
-			/* Fill remainder of buffer. */
-			size_t remainder = BUFFER_SIZE - *written_bytes;
-			dbg_zdump_detail("zdump: write_wrapper: "
-			                 "Flushing buffer, "
-			                 "appending %zu bytes.\n", remainder);
-			int ret = write_to_stream(src, 1,
-			                          remainder,
-			                          stream,
-			                          BUFFER_SIZE,
-			                          written_bytes);
-			if (ret != KNOT_EOK) {
-				dbg_zdump("zdump: write_wrapper: "
-				          "Could not write to stream: %s\n",
-				          knot_strerror(ret));
-				// failure
-				return 0;
-			}
-
-			assert(*written_bytes == BUFFER_SIZE);
-
-			/* Buffer is filled, write to the actual file. */
-			ret = write_to_file_crc(stream, 1,
-			                        *written_bytes, fd, crc);
-			if (!ret) {
-				dbg_zdump("zdump: write_wrapper: "
-				          "Could not write to file.\n");
-				// failure
-				return 0;
-			}
-			
-			/* Reset counter. */
-			*written_bytes = 0;
-			
-			/* Write remaining data to new buffer. */
-			if ((size * n) - remainder > BUFFER_SIZE) {
-				/* Write through. */
-				dbg_zdump("zdump: Attempting buffer write "
-				          "through. Total: %zu bytes.\n",
-				          (size * n) - remainder);
-				ret = write_to_file_crc(src + remainder, 1,
-				                        (size * n) - remainder,
-				                        fd, crc);
-				if (!ret) {
-					dbg_zdump("zdump: write_wrapper: "
-					          "Could not write rest of buffer to "
-					          "file: %s.\n", knot_strerror(ret));
-					// failure
-					return 0;
-				}
-			} else {
-				/* Normal buffer filling. */
-				ret = write_to_stream(src + remainder,
-				                      1, (size * n) - remainder,
-				                      stream, BUFFER_SIZE,
-				                      written_bytes);
-				if (ret != KNOT_EOK) {
-					dbg_zdump("zdump: write_wrapper: "
-					          "Could not write rest of buffer to "
-					          "stream: %s.\n", knot_strerror(ret));
-					// failure
-					return 0;
-				}
-			}
-
-			// OK
-			return 1;
-		}
-	}
-}
-
-/*!
- * \brief Dumps dname labels in binary format to given file.
- *
- * \param dname Dname whose labels are to be dumped.
- * \param f Output file.
- */
-static int knot_labels_dump_binary(const knot_dname_t *dname, int fd,
-                                   uint8_t *stream, size_t max_size,
-                                   size_t *written_bytes, crc_t *crc)
-{
-	if (dname == NULL) {
-		dbg_zdump("zdump: dump_labels: NULL dname.\n");
-		return KNOT_EINVAL;
-	}
-	
-	uint16_t label_count = dname->label_count;
-	if (!write_wrapper(&label_count, sizeof(label_count), 1, fd, stream,
-	                   max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_labels: Could not write label count.\n");
-		return KNOT_ERROR;
-	}
-	
-	if (!write_wrapper(dname->labels, sizeof(uint8_t), dname->label_count,
-	                   fd, stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_labels: Could not write labels.\n");
-		return KNOT_ERROR;
-	}
-	
-	dbg_zdump_verb("zdump: dump_labels: Labels dumped successfully.\n");
-	return KNOT_EOK;
-}
-
-/*!
- * \brief Dumps dname in binary format to given file.
- *
- * \param dname Dname to be dumped.
- * \param f Output file.
- */
-static int knot_dname_dump_binary(const knot_dname_t *dname, int fd,
-                                  uint8_t *stream, size_t max_size,
-                                  size_t *written_bytes,
-                                  crc_t *crc)
-{
-	if (dname == NULL) {
-		dbg_zdump("zdump: dump_dname: NULL dname.\n");
-		return KNOT_EINVAL;
-	}
-	
-	/*! \todo too big */
-	uint32_t dname_size = dname->size;
-	if (!write_wrapper(&dname_size, sizeof(dname_size), 1, fd, stream,
-	                   max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_dname: Cannot write dname size.\n");
-		return KNOT_ERROR;
-	}
-	
-	if (!write_wrapper(dname->name, sizeof(uint8_t), dname->size, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_dname: Cannot write dname name.\n");
-		return KNOT_ERROR;
-	}
-	
-	dbg_zdump_verb("zdump: dump_dname: Dname dumped successfully.\n");
-	return knot_labels_dump_binary(dname, fd, stream, max_size,
-	                               written_bytes, crc);
-}
-
-/*!< \todo #1684 some global variable indicating error! */
-static int dump_dname_with_id(const knot_dname_t *dname, int fd,
-                              uint8_t *stream, size_t max_size,
-                              size_t *written_bytes, crc_t *crc)
-{
-	if (dname == NULL) {
-		dbg_zdump("zdump: dump_dname: NULL dname.\n");
-		return KNOT_EINVAL;
-	}
-	
-	uint32_t id = dname->id;
-	if (!write_wrapper(&id, sizeof(id), 1, fd, stream, max_size,
-	                   written_bytes, crc)) {
-		dbg_zdump("zdump: dump_dname: Cannot write ID.\n");
-		return KNOT_ERROR;
-	}
-	return knot_dname_dump_binary(dname, fd, stream, max_size,
-	                              written_bytes, crc);
-}
-
-/*!
- * \brief Dumps given rdata in binary format to given file.
- *
- * \param rdata Rdata to be dumped.
- * \param type Type of rdata.
- * \param data Arguments to be propagated.
- */
-static int knot_rdata_dump_binary(knot_rdata_t *rdata,
-                                  uint32_t type, int fd, int use_ids,
-                                  uint8_t *stream, size_t max_size,
-                                  size_t *written_bytes,
-                                  crc_t *crc)
-{
-	if (rdata == NULL) {
-		dbg_zdump("zdump: dump_rdata: NULL rdata.\n");
-		return KNOT_EINVAL;
-	}
-	knot_rrtype_descriptor_t *desc =
-		knot_rrtype_descriptor_by_type(type);
-	assert(desc != NULL);
-
-	if (desc->fixed_items) {
-		assert(desc->length == rdata->count);
-	}
-	
-	/* Write rdata count. */
-	if (!write_wrapper(&(rdata->count),
-	                   sizeof(rdata->count), 1, fd, stream, max_size,
-	                   written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rdata: Could not write RDATA count.\n");
-		return KNOT_ERROR;
-	}
-
-	for (int i = 0; i < rdata->count; i++) {
-		dbg_zdump_detail("zdump: dump_rdata: Dumping item nr: %d\n", i);
-		if (desc->wireformat[i] == KNOT_RDATA_WF_COMPRESSED_DNAME ||
-		desc->wireformat[i] == KNOT_RDATA_WF_UNCOMPRESSED_DNAME ||
-		desc->wireformat[i] == KNOT_RDATA_WF_LITERAL_DNAME )	{
-			/*  some temp variables - this is way too long */
-			assert(rdata->items[i].dname != NULL);
-			knot_dname_t *wildcard = NULL;
-
-			if (rdata->items[i].dname->node != NULL &&
-				rdata->items[i].dname->node->owner !=
-				rdata->items[i].dname) {
-				wildcard = rdata->items[i].dname->node->owner;
-			}
-			
-			dbg_zdump_detail("zdump: dump_rdata: "
-			                 "Writing dname: %s.\n",
-			                 knot_dname_to_str(
-						rdata->items[i].dname));
-
-			if (use_ids) {
-				/* Write ID. */
-				assert(rdata->items[i].dname->id != 0);
-
-				uint32_t id = rdata->items[i].dname->id;
-				if (!write_wrapper(&id,
-				                   sizeof(id),
-				                   1, fd, stream, max_size,
-				                   written_bytes, crc)) {
-					dbg_zdump("zdump: dump_rdata: Cannot "
-					          "write dname ID.\n");
-					return KNOT_ERROR;
-				}
-			} else {
-				int ret = dump_dname_with_id(
-				                        rdata->items[i].dname,
-				                        fd, stream,
-				                        max_size,
-				                        written_bytes,
-				                        crc);
-				if (ret != KNOT_EOK) {
-					dbg_zdump("zdump: dump_rdata: Cannot "
-					          "dump dname.\n");
-					return ret;
-				}
-			}
-
-			/* Write in the zone bit */
-			/*! \todo Does not have to be so complex.
-			 *        Create extra variable. */
-			if (rdata->items[i].dname->node != NULL && !wildcard) {
-				dbg_zdump("zdump: dump_rdata: "
-				          "This dname is in the zone.\n");
-				if (!write_wrapper((uint8_t *)"\1",
-				                   sizeof(uint8_t), 1, fd,
-				                   stream, max_size,
-				                   written_bytes, crc)) {
-					dbg_zdump("zdump: dump_rdata: Cannot "
-					          "write zone bit.\n");
-					return KNOT_ERROR;
-				}
-			} else {
-				dbg_zdump("zdump: dump_rdata: "
-				          "This dname is not in the zone.\n");
-				if (!write_wrapper((uint8_t *)"\0",
-				                   sizeof(uint8_t),
-				                   1, fd,
-				                   stream, max_size,
-				                   written_bytes, crc)) {
-					dbg_zdump("zdump: dump_rdata: Cannot "
-					          "write zone bit.\n");
-					return KNOT_ERROR;
-				}
-			}
-
-			if (use_ids && wildcard) {
-				if (!write_wrapper((uint8_t *)"\1",
-				                   sizeof(uint8_t), 1,
-				                   fd, stream, max_size,
-				                   written_bytes, crc)) {
-					dbg_zdump("zdump: dump_rdata: Cannot "
-					          "write wildcard bit.\n");
-					return KNOT_ERROR;
-				}
-				
-				uint32_t wildcard_id = wildcard->id;
-				dbg_zdump("zdump: dump_rdata: "
-				          "This dname is covered by wc (%s).\n",
-				          knot_dname_to_str(wildcard));
-				if (!write_wrapper(&wildcard_id,
-				                   sizeof(wildcard_id), 1,
-				                   fd, stream, max_size,
-				                   written_bytes, crc)) {
-					dbg_zdump("zdump: dump_rdata: Cannot "
-					          "write wildcard ID.\n");
-					return KNOT_ERROR;
-				}
-			} else {
-				if (!write_wrapper((uint8_t *)"\0",
-				                   sizeof(uint8_t),
-				                   1, fd, stream,
-				                   max_size, written_bytes,
-				                   crc)) {
-					dbg_zdump("zdump: dump_rdata: Cannot "
-					          "write wildcard bit.\n");
-					return KNOT_ERROR;
-				}
-			}
-		} else {
-			dbg_zdump_detail("zdump: dump_rdata: "
-			                 "Writing raw data. Item nr.: %d\n",
-			                 i);
-			assert(rdata->items[i].raw_data != NULL);
-			if (!write_wrapper(rdata->items[i].raw_data,
-			                   sizeof(uint8_t),
-			                   rdata->items[i].raw_data[0] + 2, fd,
-			                   stream, max_size,
-			                   written_bytes, crc)) {
-				dbg_zdump("zdump: dump_rdata: Cannot write raw "
-				          "data.\n");
-				return KNOT_ERROR;
-			}
-
-			dbg_zdump_detail("zdump: dump_rdata: "
-			                  "Written %d long raw data.\n",
-					  rdata->items[i].raw_data[0]);
-		}
-	}
-	
-	dbg_zdump_verb("zdump: dump_rdata: RDATA dumped successfully.\n");
-	return KNOT_EOK;
-}
-
-/*!
- * \brief Dumps RRSIG in binary format to given file.
- *
- * \param rrsig RRSIG to be dumped.
- * \param data Arguments to be propagated.
- *
- * \todo This whole function is obsolete. Change after 1.0.2 release.
- */
-static int knot_rrsig_set_dump_binary(knot_rrset_t *rrsig, int fd,
-                                      int use_ids,
-                                      uint8_t *stream, size_t max_size,
-                                      size_t *written_bytes, crc_t *crc)
-{
-	if (rrsig == NULL) {
-		dbg_zdump("zdump: dump_rrsig: NULL RRSIG.\n");
-		return KNOT_EINVAL;
-	}
-	
-dbg_zdump_exec_detail(
-	char *name = knot_dname_to_str(knot_rrset_owner(rrsig));
-	dbg_zdump_detail("zdump: dump_rrsig: Dumping RRSIG \\w owner: %s.\n",
-	                 name);
-	free(name);
-);
-	assert(rrsig->type == KNOT_RRTYPE_RRSIG);
-	assert(rrsig->rdata);
-	if (!write_wrapper(&rrsig->type, sizeof(rrsig->type), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrsig: Cannot write type.\n");
-		return KNOT_ERROR;
-	}
-	
-	if (!write_wrapper(&rrsig->rclass, sizeof(rrsig->rclass), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrsig: Cannot write class.\n");
-		return KNOT_ERROR;
-	}
-	
-	if (!write_wrapper(&rrsig->ttl, sizeof(rrsig->ttl), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrsig: Cannot write TTL.\n");
-		return KNOT_ERROR;
-	}
-	
-	uint32_t rdata_count = 1;
-	/* Calculate rrset rdata count. */
-	knot_rdata_t *tmp_rdata = rrsig->rdata;
-	while(tmp_rdata->next != rrsig->rdata) {
-		tmp_rdata = tmp_rdata->next;
-		rdata_count++;
-	}
-	
-	if (!write_wrapper(&rdata_count, sizeof(rdata_count), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrsig: Cannot write rdata count.\n");
-		return KNOT_ERROR;
-	}
-
-	dbg_zdump_verb("zdump: dump_rrsig: Static data dumped.\n");
-
-	tmp_rdata = rrsig->rdata;
-	while (tmp_rdata->next != rrsig->rdata) {
-		int ret = knot_rdata_dump_binary(tmp_rdata, KNOT_RRTYPE_RRSIG,
-		                                 fd,
-		                                 use_ids, stream, max_size,
-		                                 written_bytes, crc);
-		if (ret != KNOT_EOK) {
-			dbg_zdump("zdump: rrsig_to_binary: Could not dump "
-			          "rdata. Reason: %s.\n", knot_strerror(ret));
-			return ret;
-		}
-		tmp_rdata = tmp_rdata->next;
-	}
-	return knot_rdata_dump_binary(tmp_rdata, KNOT_RRTYPE_RRSIG, fd, use_ids,
-	                       stream, max_size, written_bytes, crc);
-}
-
-/*!
- * \brief Dumps RRSet in binary format to given file.
- *
- * \param rrset RRSSet to be dumped.
- * \param data Arguments to be propagated.
- */
-static int knot_rrset_dump_binary(const knot_rrset_t *rrset, int fd,
-                                  int use_ids,
-                                  uint8_t *stream, size_t max_size,
-                                  size_t *written_bytes,
-                                  crc_t *crc)
-{
-	if (rrset == NULL) {
-		dbg_zdump("zdump: dump_rrset: NULL RRSet.\n");
-		return KNOT_EINVAL;
-	}
-	
-	dbg_zdump_exec_detail(
-		char *name = knot_dname_to_str(knot_rrset_owner(rrset));
-		dbg_zdump_detail("zdump: dump_rrset: "
-	                         "Dumping RRSet \\w owner: %s.\n",
-		                 name);
-		free(name);
-	);
-		
-	if (!use_ids) {
-		assert(rrset->rrsigs == NULL);
-	}
-	
-	if (!use_ids) {
-		/*!< \todo IDs in changeset do no good. Change loading too. */
-		int ret = dump_dname_with_id(rrset->owner,
-		                             fd, stream, max_size,
-		                             written_bytes, crc);
-		if (ret != KNOT_EOK) {
-			dbg_zdump("zdump: rrset_dump_binary: Could not dump "
-			          "RRSet's owner.\n");
-			return ret;
-		}
-	}
-
-	if (!write_wrapper(&rrset->type, sizeof(rrset->type), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrset: Cannot write type.\n");
-		return KNOT_ERROR;
-	}
-	if (!write_wrapper(&rrset->rclass, sizeof(rrset->rclass), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrset: Cannot write class.\n");
-		return KNOT_ERROR;
-	}
-	if (!write_wrapper(&rrset->ttl, sizeof(rrset->ttl), 1, fd,
-	               stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrset: Cannot write TTL.\n");
-		return KNOT_ERROR;
-	}
-
-	uint32_t rdata_count = 1;
-	uint8_t has_rrsig = rrset->rrsigs != NULL;
-
-	/* Calculate rrset rdata count. */
-	knot_rdata_t *tmp_rdata = rrset->rdata;
-	while(tmp_rdata && (tmp_rdata->next != rrset->rdata)) {
-		tmp_rdata = tmp_rdata->next;
-		rdata_count++;
-	}
-	
-	if (rrset->rdata == NULL) {
-		rdata_count = 0;
-	}
-
-	if (!write_wrapper(&rdata_count, sizeof(rdata_count), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_rrset: Cannot write rdata count.\n");
-		return KNOT_ERROR;
-	}
-	
-	if (!write_wrapper(&has_rrsig, sizeof(has_rrsig), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		return KNOT_ERROR;
-	}
-	
-	dbg_zdump_verb("zdump: rrset_dump_binary: Static data dumped.\n");
-	
-	if (rdata_count != 0) {
-	
-		tmp_rdata = rrset->rdata;
-
-		while (tmp_rdata->next != rrset->rdata) {
-			int ret = knot_rdata_dump_binary(tmp_rdata, rrset->type,
-			                                 fd, use_ids,
-			                                 stream, max_size,
-			                                 written_bytes, crc);
-			if (ret != KNOT_EOK) {
-				dbg_zdump("zdump: rrset_to_binary: Could not "
-				          "dump "
-				          "rdata. Reason: %s.\n",
-				          knot_strerror(ret));
-				return ret;
-			}
-			tmp_rdata = tmp_rdata->next;
-		}
-	
-		int ret = knot_rdata_dump_binary(tmp_rdata, rrset->type,
-		                                 fd, use_ids,
-		                                 stream,
-		                                 max_size, written_bytes, crc);
-		if (ret != KNOT_EOK) {
-			dbg_zdump("zdump: rrset_to_binary: Could not dump "
-			          "rdata. Reason: %s.\n", knot_strerror(ret));
-			return ret;
-		}
-	}
-	
-	dbg_zdump_verb("zdump: rrset_dump_binary: Rdata dumped.\n");
-
-	/* This is now obsolete, although I'd rather not use recursion - that
-	 * would probably not work */
-
-	if (rrset->rrsigs != NULL) {
-		return knot_rrsig_set_dump_binary(rrset->rrsigs, fd, use_ids,
-		                                  stream,
-		                                  max_size, written_bytes, crc);
-	} else {
-		return KNOT_EOK;
-	}
-}
-
-/*!
- * \brief Dumps all RRSets in node to file in binary format.
- *
- * \param node Node to dumped.
- * \param data Arguments to be propagated.
- */
-static int knot_node_dump_binary(knot_node_t *node, int fd,
-                                 uint8_t *stream,
-                                 size_t max_size,
-                                 size_t *written_bytes,
-                                 crc_t *crc)
-{
-	if (node == NULL) {
-		dbg_zdump("zdump: dump_node: NULL node.\n");
-		return KNOT_EINVAL;
-	}
-	
-	/* first write dname */
-	assert(node->owner != NULL);
-
-	/* Write owner ID. */
-dbg_zdump_exec_detail(
-	char *name = knot_dname_to_str(knot_node_owner(node));
-	dbg_zdump_detail("zdump: dump_node: Dumping node owned by %s\n",
-	                 name);
-	free(name);
-);
-	assert(node->owner->id != 0);
-	uint32_t owner_id = node->owner->id;
-	if (!write_wrapper(&owner_id, sizeof(owner_id), 1, fd, stream,
-	                   max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_node: Cannot write ID.\n");
-		return KNOT_ERROR;
-	}
-
-	/*!< \todo Fix after release. */
-	if (knot_node_parent(node) != NULL) {
-		uint32_t parent_id = knot_dname_id(
-				knot_node_owner(knot_node_parent(node)));
-		if (!write_wrapper(&parent_id, sizeof(parent_id), 1, fd,
-		                   stream, max_size, written_bytes, crc)) {
-			dbg_zdump("zdump: dump_node: Cannot write parent "
-			          "ID.\n");
-			return KNOT_ERROR;
-		}
-	} else {
-		uint32_t parent_id = 0;
-		if (!write_wrapper(&parent_id, sizeof(parent_id), 1, fd,
-		                   stream, max_size, written_bytes, crc)) {
-			dbg_zdump("zdump: dump_node: Cannot write parent "
-			          "ID.\n");
-			return KNOT_ERROR;
-		}
-	}
-
-	if (!write_wrapper(&(node->flags), sizeof(node->flags), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_node: Cannot write node flags.\n");
-		return KNOT_ERROR;
-	}
-
-	if (knot_node_nsec3_node(node) != NULL) {
-		uint32_t nsec3_id =
-			knot_node_owner(knot_node_nsec3_node(node))->id;
-		if (!write_wrapper(&nsec3_id, sizeof(nsec3_id), 1, fd,
-		                   stream, max_size, written_bytes, crc)) {
-			dbg_zdump("zdump: dump_node: Cannot write NSEC3 ID.\n");
-			return KNOT_ERROR;
-		}
-		
-		dbg_zdump_detail("Written nsec3 node id: %u\n",
-			         knot_node_owner(
-		                         knot_node_nsec3_node(node))->id);
-	} else {
-		uint32_t nsec3_id = 0;
-		if (!write_wrapper(&nsec3_id, sizeof(nsec3_id), 1, fd,
-		                   stream, max_size, written_bytes, crc)) {
-			dbg_zdump("zdump: dump_node: Cannot write NSEC3 ID.\n");
-			return KNOT_ERROR;
-		}
-	}
-
-	/* Now we need (or do we?) count of rrsets to be read
-	 * but that number is yet unknown */
-
-	uint16_t rrset_count = node->rrset_count;
-	if (!write_wrapper(&rrset_count, sizeof(rrset_count), 1, fd,
-	                   stream, max_size, written_bytes, crc)) {
-		dbg_zdump("zdump: dump_node: Cannot write RRSet count.\n");
-		return KNOT_ERROR;
-	}
-
-	const knot_rrset_t **node_rrsets = knot_node_rrsets(node);
-	for (int i = 0; i < rrset_count; i++)
-	{
-		int ret = knot_rrset_dump_binary(node_rrsets[i], fd, 1,
-		                                 stream, max_size,
-		                                 written_bytes, crc);
-		if (ret != KNOT_EOK) {
-			dbg_zdump("zdump: dump_node: Could not dump RRSet. "
-			          "Reason: %s.\n", knot_strerror(ret));
-			return ret;
-		}
-	}
-
-	free(node_rrsets);
-	
-	dbg_zdump_verb("zdump: dump_node: Node dumped successfully.\n");
-
-	return KNOT_EOK;
-}
-
-int zone_is_secure(knot_zone_contents_t *zone)
-{
-	if (knot_node_rrset(knot_zone_contents_apex(zone),
-			      KNOT_RRTYPE_DNSKEY) == NULL) {
-		return 0;
-	} else {
-		if (knot_node_rrset(knot_zone_contents_apex(zone),
-				      KNOT_RRTYPE_NSEC3PARAM) != NULL) {
-			return 2;
-		} else {
-			return 1;
-		}
-	}
-}
-
-static void dump_dname_from_tree(knot_dname_t *dname,
-				 void *data)
-{
-	arg_t *arg = (arg_t *)data;
-	if (arg->error_code != KNOT_EOK) {
-		dbg_zdump("zdump: dump_dname_from_tree: "
-		          "Error occured previously.\n");
-		return;
-	}
-	
-	int *fd_pointer = (int *)arg->arg1;
-	int fd = -1;
-	if (fd_pointer != NULL) {
-		fd = *fd_pointer;
-	} else {
-		dbg_zdump("zdump: dump_dname_from_tree: Bad fd.\n");
-		arg->error_code = KNOT_EINVAL;
-		return;
-	}
-	
-	uint8_t *buffer = (uint8_t *)arg->arg5;
-	size_t *written_bytes = (size_t *)arg->arg6;
-	crc_t *crc = (crc_t*)arg->arg2;
-	
-	arg->error_code = dump_dname_with_id(dname, fd, buffer,
-	                                     BUFFER_SIZE, written_bytes, crc);
-}
-
-static int knot_dump_dname_table(const knot_dname_table_t *dname_table,
-				 int fd, crc_t *crc, uint8_t *buffer,
-                                 size_t *written_bytes)
-{
-	arg_t arg;
-	arg.arg2 = crc;
-	arg.arg5 = buffer;
-	arg.arg6 = written_bytes;
-	arg.arg1 = &fd;
-	assert(arg.arg1 == &fd);
-	arg.error_code = KNOT_EOK;
-	/* Go through the tree and dump each dname along with its ID. */
-	knot_dname_table_tree_inorder_apply(dname_table,
-					    dump_dname_from_tree, &arg);
-
-	return arg.error_code;
-}
-
-static void save_node_from_tree(knot_node_t *node, void *data)
-{
-	arg_t *arg = (arg_t *)data;
-	if (arg == NULL) {
-		return;
-	}
-	
-	/* Increment node count */
-	(*((uint32_t *)(arg->arg1)))++;
-	/* Save the first node only */
-	if (arg->arg2 == NULL) {
-		arg->arg2 = (void *)node;
-	}
-	arg->arg3 = (void *)node;
-}
-
-static void dump_node_to_file(knot_node_t *node, void *data)
-{
-	arg_t *arg = (arg_t *)data;
-	if (arg == NULL) {
-		return;
-	}
-	
-	if (arg->error_code != KNOT_EOK) {
-		dbg_zdump("zdump: dump_node_to_file: "
-		          "Error occured previously.\n");
-		return;
-	}
-	
-	int *fd_pointer = (int *)arg->arg1;
-	int fd = -1;
-	if (fd_pointer != NULL) {
-		fd = *fd_pointer;
-	}
-	
-	uint8_t *buffer = (uint8_t *)arg->arg5;
-	size_t *written_bytes = (size_t *)arg->arg6;
-	
-	arg->error_code =
-		knot_node_dump_binary(node,
-	                              fd, buffer, BUFFER_SIZE, written_bytes,
-	                              (crc_t *)arg->arg7);
-}
-
-char *knot_zdump_crc_file(const char* filename)
-{
-	char *crc_path =
-		malloc(sizeof(char) * (strlen(filename) +
-		strlen(".crc") + 1));
-	CHECK_ALLOC_LOG(crc_path, NULL);
-	memset(crc_path, 0,
-	       sizeof(char) * (strlen(filename) +
-	       strlen(".crc") + 1));
-	memcpy(crc_path, filename,
-	       sizeof(char) * strlen(filename));
-	crc_path = strncat(crc_path, ".crc", strlen(".crc"));
-	return crc_path;
-}
-
-int knot_zdump_binary(knot_zone_contents_t *zone, int fd,
-                      int do_checks, const char *sfilename,
-                      crc_t *crc)
-{
-
-	if (fd < 0 || sfilename == NULL) {
-		dbg_zdump("zdump: Bad arguments.\n");
-		return KNOT_EINVAL;
-	}
-	
-	dbg_zdump("zdump: Dumping zone %p.\n", zone);
-	
-	uint8_t buffer[BUFFER_SIZE];
-	size_t written_bytes = 0;
-
-	arg_t arguments;
-	/* Memory to be derefenced in the save_node_from_tree function. */
-	uint32_t node_count = 0;
-	arguments.arg1 = &node_count;
-	arguments.arg2 = NULL;
-
-	/* Count number of normal nodes. This cannot fail. */
-	knot_zone_contents_tree_apply_inorder(zone, save_node_from_tree,
-	                                      &arguments);
-	/* arg1 is now count of normal nodes */
-	uint32_t normal_node_count = *((uint32_t *)arguments.arg1);
-
-	node_count = 0;
-	arguments.arg1 = &node_count;
-	arguments.arg2 = NULL;
-
-	/* Count number of NSEC3 nodes. This cannot fail. */
-	knot_zone_contents_nsec3_apply_inorder(zone,
-	                                       save_node_from_tree, &arguments);
-	uint32_t nsec3_node_count = *((uint32_t *)arguments.arg1);
-	/* arg2 is the first NSEC3 node - used in sem checks. */
-	/* arg3 is the last NSEC3 node - used in sem checks. */
-	const knot_node_t *first_nsec3_node = (knot_node_t *)arguments.arg2;
-	const knot_node_t *last_nsec3_node = (knot_node_t *)arguments.arg3;
-
-	if (do_checks && zone_is_secure(zone)) {
-		do_checks += zone_is_secure(zone);
-	}
-
-	/* FIXME(OS): Really descriptive call 1,1,1,1, some #defines here? */
-	err_handler_t *handler = handler_new(1, 1, 1, 1, 1);
-	if (handler == NULL) {
-		return KNOT_ENOMEM;
-	} else { /* Do check for SOA right now */
-		if (knot_node_rrset(knot_zone_contents_apex(zone),
-				      KNOT_RRTYPE_SOA) == NULL) {
-			err_handler_handle_error(handler,
-						 knot_zone_contents_apex(zone),
-						 ZC_ERR_MISSING_SOA,
-			                         NULL);
-		}
-	}
-	
-	knot_node_t *last_node = NULL;
-	int ret = zone_do_sem_checks(zone,
-	                             do_checks, handler, &last_node);
-	log_cyclic_errors_in_zone(handler, zone, last_node,
-	                          first_nsec3_node, last_nsec3_node,
-	                          do_checks);
-	err_handler_log_all(handler);
-	free(handler);
-		
-	if (ret != KNOT_EOK) {
-		fprintf(stderr, "Zone will not be dumped because of "
-		        "fatal semantic errors.\n");
-		/* If remove fails, there is nothing we can do. */
-		return KNOT_ERROR;
-	}
-
-	*crc = crc_init();
-
-	/* Start writing header - magic bytes. */
-	static const uint8_t MAGIC[MAGIC_LENGTH] = MAGIC_BYTES;
-	if (!write_wrapper(&MAGIC, sizeof(uint8_t), MAGIC_LENGTH,
-	                   fd, buffer, BUFFER_SIZE, &written_bytes, crc)) {
-		dbg_zdump("zdump: Cannot write magic bytes.\n");
-		return KNOT_ERROR;
-	}
-
-	/* Write source file length. */
-	uint32_t sflen = strlen(sfilename) + 1;
-	if (!write_wrapper(&sflen, sizeof(uint32_t), 1, fd,
-	                   buffer, BUFFER_SIZE, &written_bytes, crc)) {
-		dbg_zdump("zdump: Cannot write source file length.\n");
-		return KNOT_ERROR;
-	}
-
-	/* Write source file. */
-	if (!write_wrapper(sfilename, sflen, 1, fd,  buffer,
-	                   BUFFER_SIZE, &written_bytes, crc)) {
-		dbg_zdump("zdump: Cannot write source file name.\n");
-		return KNOT_ERROR;
-	}
-
-	/* Notice: End of header,
-	 */
-
-	/* Start writing compiled data. */
-	if (!write_wrapper(&normal_node_count, sizeof(normal_node_count), 1, fd,
-	                    buffer, BUFFER_SIZE, &written_bytes, crc)) {
-		dbg_zdump("zdump: Cannot write node count.\n");
-		return KNOT_ERROR;
-	}
-	
-	if (!write_wrapper(&nsec3_node_count, sizeof(nsec3_node_count), 1, fd,
-	                   buffer, BUFFER_SIZE, &written_bytes, crc)) {
-		dbg_zdump("zdump: Cannot write NSEC3 node count.\n");
-		return KNOT_ERROR;
-	}
-	uint32_t auth_node_count = zone->node_count;
-	if (!write_wrapper(&auth_node_count,
-	                   sizeof(auth_node_count),
-	                   1, fd,  buffer, BUFFER_SIZE, &written_bytes, crc)) {
-		dbg_zdump("zdump: Cannot write authoritative node count.\n");
-		return KNOT_ERROR;
-	}
-
-	/* Write total number of dnames */
-	assert(zone->dname_table);
-	uint32_t total_dnames = zone->dname_table->id_counter;
-	if (!write_wrapper(&total_dnames,
-	                   sizeof(total_dnames), 1, fd,
-	                   buffer, BUFFER_SIZE, &written_bytes, crc)) {
-		dbg_zdump("zdump: Cannot write dname count.\n");
-		return KNOT_ERROR;
-	}
-
-	/* Write dname table. */
-	if (knot_dump_dname_table(zone->dname_table, fd, crc, buffer,
-	                          &written_bytes)
-	    != KNOT_EOK) {
-		dbg_zdump("zdump: Cannot write dname table.\n");
-		return KNOT_ERROR;
-	}
-	
-	arguments.arg1 = &fd;
-	arguments.arg3 = zone;
-	arguments.arg5 = buffer;
-	arguments.arg6 = &written_bytes;
-	arguments.arg7 = crc;
-	
-	arguments.error_code = KNOT_EOK;
-
-	/*!< \todo #1685 Stop traversal upon error. */
-	knot_zone_contents_tree_apply_inorder(zone, dump_node_to_file,
-				       (void *)&arguments);
-	
-	if (arguments.error_code != KNOT_EOK) {
-		dbg_zdump("zdump: Dump of normal tree failed. Reason: %s.\n",
-		          knot_strerror(arguments.error_code));
-		return arguments.error_code;
-	}
-	
-	arguments.error_code = KNOT_EOK;
-	knot_zone_contents_nsec3_apply_inorder(zone, dump_node_to_file,
-					(void *)&arguments);
-	
-	if (arguments.error_code != KNOT_EOK) {
-		dbg_zdump("zdump: Dump of NSEC3 tree failed. Reason: %s.\n",
-		          knot_strerror(arguments.error_code));
-		return arguments.error_code;
-	}
-	
-	/* Finish the dump. */
-	if (!write_to_file_crc(buffer, 1, written_bytes, fd, crc)) {
-		fprintf(stderr, "Failed to finalize zone db!\n");
-		return KNOT_ERROR;
-	}
-	
-	*crc = crc_finalize(*crc);
-	dbg_zdump("zdump: Zone %p dumped successfully.\n", zone);
-	
-	return KNOT_EOK;
-}
-
-int knot_zdump_rrset_serialize(const knot_rrset_t *rrset, uint8_t *stream,
-                                 size_t max_size, size_t *written_bytes)
-{
-	if (stream == NULL || rrset == NULL ||
-	    written_bytes == NULL) {
-		dbg_zdump("zdump: rrset_serialize: Bad arguments.\n");
-		return KNOT_EINVAL;
-	}
-	
-	*written_bytes = 0;
-
-	/* This fd will signal functions to use streams. */
-	int fd = -1;
-
-	return knot_rrset_dump_binary(rrset, fd, 0, stream, max_size,
-	                              written_bytes, NULL);
-}
-
-int knot_zdump_dump(knot_zone_contents_t *zone, int fd, const char *sfilename,
-                    crc_t *crc)
-{
-	int rc = knot_zdump_binary(zone, fd, 0, sfilename, crc);
-	if (rc != KNOT_EOK) {
-		dbg_zdump("Failed to save the zone to binary zone db\n.");
-		return KNOT_ERROR;
-	}
-
-	return KNOT_EOK;
-}
diff --git a/src/knot/zone/zone-dump.h b/src/knot/zone/zone-dump.h
deleted file mode 100644
index 538cb87ea9f10a38b90912d272cd2bcd37507dcc..0000000000000000000000000000000000000000
--- a/src/knot/zone/zone-dump.h
+++ /dev/null
@@ -1,97 +0,0 @@
-/*  Copyright (C) 2011 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
- */
-/*!
- * \file zone-dump.h
- *
- * \author Jan Kadlec <jan.kadlec@nic.cz>
- *
- * \brief Functions for dumping zone to binary file.
- *
- * \addtogroup zone-load-dump
- * @{
- */
-
-#ifndef _KNOT_ZONEDUMP_H_
-#define _KNOT_ZONEDUMP_H_
-
-#include "common/crc.h"
-#include "libknot/zone/zone.h"
-
-/*!
- * \brief Zone loader enums.
- */
-enum {
-	MAGIC_LENGTH = 7 /*!< Compiled zone magic length. */
-};
-
-/*! \brief Magic identifier: { "knot", maj_ver, min_ver, revision } */
-#define MAGIC_BYTES {'k', 'n', 'o', 't', '1', '1', '0'}
-
-/*!
- * \brief Dumps given zone to binary file.
- *
- * \param zone Zone to be saved.
- * \param fd File descriptor to be written to.
- * \param do_checks Set to 1 to enable checking the zone for semantic errors.
- * \param sfilename Source filename of the text zone file.
- * \param crc Returns a calculated CRC.
- *
- * \retval KNOT_EOK on success.
- * \retval KNOT_EINVAL if the file cannot be opened for writing.
- */
-int knot_zdump_binary(knot_zone_contents_t *zone, int fd,
-                      int do_checks, const char *sfilename,
-                      crc_t *crc);
-
-/*!
- * \brief Serializes RRSet into binary stream. Expects NULL pointer, memory
- *        is handled inside function.
- *
- * \param rrset RRSet to be serialized.
- * \param stream Stream containing serialized RRSet.
- * \param max_size Maximum size of stream.
- * \param bytes_written Actually written data.
- *
- * \retval KNOT_EOK on success.
- * \retval KNOT_EINVAL if wrong arguments are supplied.
- * \retval KNOT_ENOMEM on memory error.
- */
-int knot_zdump_rrset_serialize(const knot_rrset_t *rrset, uint8_t *stream,
-                               size_t max_size, size_t *bytes_written);
-
-/*!
- * \brief Checks if zone uses DNSSEC and/or NSEC3
- *
- * \param zone Zone to be checked.
- *
- * \retval 0 if zone is not secured.
- * \retval 2 if zone uses NSEC3
- * \retval 1 if zone uses NSEC
- */
-int zone_is_secure(knot_zone_contents_t *zone);
-
-/*! \todo Document me (issue #1586). */
-int knot_zdump_dump(knot_zone_contents_t *zone, int fd, const char *sfilename,
-                    crc_t *crc);
-
-/*!
- * \brief Return name of the CRC file associated with filename.
- */
-char *knot_zdump_crc_file(const char* filename);
-
-#endif /* _KNOT_ZONEDUMP_H_ */
-
-/*! @} */
diff --git a/src/knot/zone/zone-load.c b/src/knot/zone/zone-load.c
index 813a62793c07ef29f5cee7efca000ad0ca967d95..99c502368815b81c817f7c24c53db3886ea91fa6 100644
--- a/src/knot/zone/zone-load.c
+++ b/src/knot/zone/zone-load.c
@@ -30,8 +30,8 @@
 #include "libknot/common.h"
 #include "knot/other/debug.h"
 #include "knot/zone/zone-load.h"
-#include "knot/zone/zone-dump.h"
 #include "libknot/libknot.h"
+#include "zscanner/file_loader.h"
 
 /*!
  * \brief Compares two time_t values.
@@ -50,1158 +50,623 @@ static int timet_cmp(time_t x, time_t y)
 	return 0;
 }
 
-/*!
- * \brief Safe wrapper around fread.
- *
- * \param dst Destination pointer.
- * \param size Size of element to be read.
- * \param n Number of elements to be read.
- * \param fp File to read from.
- *
- * \retval > 0 if succesfull.
- * \retval 0 if failed.
- */
-static inline int fread_safe_from_file(void *dst,
-                                       size_t size, size_t n, void *source)
-{
-	if (dst == NULL || source == NULL) {
-		dbg_zload("zload: fread_safe_from_file: NULL arguments.\n");
-		return 0;
-	}
-	FILE *fp = (FILE *)source;
-	int rc = fread(dst, size, n, fp);
-	if (rc != n) {
-		dbg_zload("zload: fread_safe_from_file: "
-		          "invalid read %d (exp. %zu)\n",
-			  rc, n);
-	}
-
-	return rc == n;
-}
-
-struct load_stream {
-	uint8_t *stream;
-	size_t stream_remaining;
-	size_t stream_size;
-};
-
-typedef struct load_stream load_stream_t;
-
-static inline int read_from_stream(void *dst,
-                                   size_t size, size_t n, void *source)
-{
-	if (dst == NULL || source == NULL) {
-		dbg_zload("zload: read_from_stream: NULL arguments.\n");
-		return 0;
-	}
-	
-	/* Extract information from source data. */
-	load_stream_t *data = (load_stream_t *)source;
-	
-	
-	if (data->stream_remaining < (size * n)) {
-		dbg_zload("zload: read_from_stream: Buffer depleted.\n");
-		return 0;
-	}
+/* ZONE LOADING FROM FILE USING RAGEL PARSER */
 
-	memcpy(dst,
-	       data->stream +
-	       (data->stream_size - data->stream_remaining),
-	       size * n);
-	data->stream_remaining -= size * n;
 
-	return 1;
-}
-
-/*! \note Contents of dump file:
- * MAGIC(knotxx) NUMBER_OF_NORMAL_NODES NUMBER_OF_NSEC3_NODES
- * [normal_nodes] [nsec3_nodes]
- * node has following format:
- * owner_size owner_wire owner_label_size owner_labels owner_id
- * node_flags node_rrset_count [node_rrsets]
- * rrset has following format:
- * rrset_type rrset_class rrset_ttl rrset_rdata_count rrset_rrsig_count
- * [rrset_rdata] [rrset_rrsigs]
- * rdata can either contain full dnames (that is with labels but without ID)
- * or dname ID, if dname is in the zone
- * or raw data stored like this: data_len [data]
- */
+// TODO remove once debugging is done
+static long rr_count = 0;
+static long new_rr_count = 0;
+static long new_dname_count = 0;
+static long err_count = 0;
 
-enum { DNAME_MAX_WIRE_LENGTH = 256 };
 
 /*!
- * \brief Helper function. Frees rdata items and temporary array of items.
+ * \brief Adds RRSet to list.
  *
- * \param rdata Rdata to be freed.
- * \param items Items to be freed.
- * \param count Current count of rdata items.
- * \param type RRSet type.
+ * \param head Head of list.
+ * \param rrsig RRSet to be added.
  */
-static void load_rdata_purge(knot_rdata_t *rdata,
-			     knot_rdata_item_t *items,
-			     int count,
-			     knot_rrtype_descriptor_t *desc,
-			     uint16_t type)
+static int rrset_list_add(rrset_list_t **head, knot_rrset_t *rrsig)
 {
-	/* Increase refcount manually, as the set_items() doesn't see the dname
-	 * type and thus is unable to increment refcounter.
-	 */
-	for (int i = 0; i < count; ++i) {
-		switch(desc->wireformat[i]) {
-		case KNOT_RDATA_WF_COMPRESSED_DNAME:
-		case KNOT_RDATA_WF_UNCOMPRESSED_DNAME:
-		case KNOT_RDATA_WF_LITERAL_DNAME:
-				knot_dname_retain(items[i].dname);
-			break;
-		default:
-			/*!< \todo This would leak wire data! */
-			break;
-		}
-	}
-
-	/* Copy items to rdata and free the temporary rdata. */
-	knot_rdata_set_items(rdata, items, count);
-	knot_rdata_deep_free(&rdata, type, 0);
-	free(items);
-}
-
-static knot_dname_t *read_dname_with_id(FILE *f, int use_ids)
-{
-	if (f == NULL) {
-		dbg_zload("zload: read_dname_id: NULL file.\n");
-	}
-	knot_dname_t *ret = knot_dname_new();
-	CHECK_ALLOC_LOG(ret, NULL);
-	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	if (use_ids) {
-		fread_wrapper = fread_safe_from_file;
+	if (*head == NULL) {
+		*head = xmalloc(sizeof(rrset_list_t));
+		(*head)->next = NULL;
+		(*head)->data = rrsig;
 	} else {
-		fread_wrapper = read_from_stream;
-	}
-
-	/* Read ID. */
-	uint32_t dname_id = 0;
-	if (!fread_wrapper(&dname_id, sizeof(dname_id), 1, f)) {
-		knot_dname_release(ret);
-		dbg_zload("zload: read_dname_id: Cannot read dname ID.\n");
-		return NULL;
-	}
-
-	ret->id = dname_id;
-	dbg_zload_detail("zload: read_dname_id: dname id: %u\n", dname_id);
-
-	/* Read size of dname. */
-	uint32_t dname_size = 0;
-	if (!fread_wrapper(&dname_size, sizeof(dname_size), 1, f)) {
-		knot_dname_release(ret);
-		dbg_zload("zload: read_dname_id: Cannot read dname size.\n");
-		return NULL;
-	}
-	ret->size = dname_size;
-	dbg_zload_detail("loaded: dname length: %u\n", ret->size);
-	if (ret->size > DNAME_MAX_WIRE_LENGTH) {
-		dbg_zload("zload: read_dname_id: Name too long.\n");
-		knot_dname_release(ret);
-		return NULL;
-	}
-
-	/* Read wireformat of dname. */
-	ret->name = malloc(sizeof(uint8_t) * ret->size);
-	if (ret->name == NULL) {
-		ERR_ALLOC_FAILED;
-		knot_dname_release(ret);
-		return NULL;
-	}
-
-	if (!fread_wrapper(ret->name, sizeof(uint8_t), ret->size, f)) {
-		knot_dname_release(ret);
-		dbg_zload("zload: read_dname_id: Cannot read dname name.\n");
-		return NULL;
-	}
-
-	/* Read labels. */
-	uint16_t label_count = 0;
-	if (!fread_wrapper(&label_count, sizeof(label_count), 1, f)) {
-		knot_dname_release(ret);
-		dbg_zload("zload: read_dname_id: Cannot read "
-		          "dname label count.\n");
-		return NULL;
-	}
-
-	ret->label_count = label_count;
-
-	ret->labels = malloc(sizeof(uint8_t) * ret->label_count);
-	if (ret->labels == NULL) {
-		ERR_ALLOC_FAILED;
-		knot_dname_release(ret);
-		return NULL;
+		rrset_list_t *tmp = xmalloc(sizeof(*tmp));
+		tmp->next = *head;
+		tmp->data = rrsig;
+		*head = tmp;
 	}
+	
+	dbg_zp_verb("zp: rrset_add: Added RRSIG %p to list.\n", rrsig);
 
-	if (!fread_wrapper(ret->labels, sizeof(uint8_t), ret->label_count, f)) {
-		free(ret->name);
-		free(ret);
-		dbg_zload("zload: read_dname_id: Cannot read dname labels.\n");
-		return NULL;
-	}
-
-dbg_zload_exec_detail(
-	char *name = knot_dname_to_str(ret);
-	dbg_zload_detail("zload: Loaded dname: %s (id: %d).\n", name,
-			 ret->id);
-	free(name);
-);
-
-	return ret;
+	return KNOT_EOK;
 }
 
 /*!
- * \brief Load rdata in binary format from file.
+ * \brief Deletes RRSet list. Sets pointer to NULL.
  *
- * \param type Type of RRSet containing read rdata.
- * \param f File to read binary data from.
- *
- * \return Pointer to read and created rdata on success, NULL otherwise.
+ * \param head Head of list to be deleted.
  */
-static knot_rdata_t *knot_load_rdata(uint16_t type, FILE *f,
-                                         knot_dname_t **id_array,
-                                         int use_ids)
+static void rrset_list_delete(rrset_list_t **head)
 {
-	if (f == NULL) {
-		dbg_zload("zload: load_rdata: NULL arguments.\n");
-		return NULL;
-	}
-	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	if (use_ids) {
-		fread_wrapper = fread_safe_from_file;
-	} else {
-		fread_wrapper = read_from_stream;
-	}
-	
-	knot_rdata_t *rdata = knot_rdata_new();
-	if (rdata == NULL) {
-		dbg_zload("zload: load_rdata: Cannot create new rdata.\n");
-		return NULL;
-	}
-
-	knot_rrtype_descriptor_t *desc =
-		knot_rrtype_descriptor_by_type(type);
-	assert(desc != NULL);
-
-	/* First we should read rdata count. */
-
-	uint32_t rdata_count = 0;
-
-	if(!fread_wrapper(&rdata_count, sizeof(rdata_count), 1, f)) {
-		knot_rdata_free(&rdata);
-		dbg_zload("zload: load_rdata: Cannot read rdata count.\n");
-		return NULL;
-	}
-
-	knot_rdata_item_t *items =
-		malloc(sizeof(knot_rdata_item_t) * rdata_count);
-	if (items == NULL) {
-		ERR_ALLOC_FAILED;
-		free(rdata);
-		return NULL;
-	}
-
-	if (rdata_count > desc->length) {
-		dbg_zload("zload: load_rdata: Read wrong count of RDATA.\n");
-		free(items);
-		free(rdata);
-		return NULL;
-	}
-
-	uint16_t raw_data_length = 0;
-
-	dbg_zload_detail("zload: load_rdata: Reading %d items\n", rdata_count);
-	dbg_zload_detail("zload: load_rdata: Current type: %u\n", type);
-
-	for (int i = 0; i < rdata_count; i++) {
-		if (desc->wireformat[i] == KNOT_RDATA_WF_COMPRESSED_DNAME ||
-		desc->wireformat[i] == KNOT_RDATA_WF_UNCOMPRESSED_DNAME ||
-		desc->wireformat[i] == KNOT_RDATA_WF_LITERAL_DNAME )	{
-
-			/*!< \todo #1686
-			 * Refactor these variables, some might be too big.
-			 */
-			
-
-			uint32_t dname_id = 0;
-			uint8_t has_wildcard = 0;
-			uint8_t in_the_zone = 0;
-
-			if (use_ids) {
-				if(!fread_wrapper(&dname_id, sizeof(dname_id),
-				                  1, f)) {
-					load_rdata_purge(rdata,
-					                 items, i, desc, type);
-					dbg_zload("zload: load_rdata: "
-					          "Cannot read dname ID.\n");
-					return NULL;
-				}
-
-				/* Store reference do dname. */
-				knot_dname_retain(id_array[dname_id]);
-				items[i].dname = id_array[dname_id];
-			} else {
-				items[i].dname = read_dname_with_id(f, use_ids);
-			}
-			
-			dbg_zload_detail("zload: load_rdata: "
-			                 "Loading dname: %s.\n",
-			              knot_dname_to_str(items[i].dname));
-
-
-			if(!fread_wrapper(&in_the_zone, sizeof(in_the_zone),
-			               1, f)) {
-				load_rdata_purge(rdata, items, i, desc, type);
-				dbg_zload("zload: load_rdata: "
-				          "Cannot read zone bit.\n");
-				return NULL;
-			}
-
-			if(!fread_wrapper(&has_wildcard, sizeof(uint8_t),
-				       1, f)) {
-				load_rdata_purge(rdata, items, i, desc, type);
-				dbg_zload("zload: load_rdata: "
-				          "Cannot read wildcard bit.\n");
-				return NULL;
-			}
-			
-			dbg_zload_detail("zload: load_rdata: Has wildcard: "
-			                 "%d\n", has_wildcard);
-			
-			if (use_ids && !in_the_zone) {
-				dbg_zload_detail("zload: load_rdata: "
-				                 "Freeing node owned by: %s.\n",
-				                 knot_dname_to_str(items[i].dname));
-				/* Destroy the node */
-				assert(!in_the_zone);
-				if (items[i].dname->node != NULL &&
-				    /*
-				     * This check is here to prevent freeing
-				     * of previously set wildcard node.
-				     */
-				    (items[i].dname->node->owner ==
-				     items[i].dname)) {
-					knot_node_free(&items[i].dname->node);
-					assert(items[i].dname->node == NULL);
-				}
-			}
-
-			if (use_ids && has_wildcard) {
-				if(!fread_wrapper(&dname_id, sizeof(dname_id),
-					       1, f)) {
-					load_rdata_purge(rdata, items,
-							 i, desc, type);
-					dbg_zload("zload: load_rdata: "
-					          "Cannot read wc ID.\n");
-					return NULL;
-				}
-				dbg_zload_detail("zload: load_rdata: "
-				                 "Wildcard: %s\n",
-				                 knot_dname_to_str(
-				                         id_array[dname_id]));
-				items[i].dname->node =
-					id_array[dname_id]->node;
-			}
-			
-			assert(items[i].dname);
-		} else {
-			if (!fread_wrapper(&raw_data_length,
-					sizeof(raw_data_length), 1, f)) {
-				load_rdata_purge(rdata, items, i, desc, type);
-				dbg_zload("zload: load_rdata: Cannot read "
-				          "raw data length.\n");
-				return NULL;
-			}
-			
-			/*!< \todo this is not proper fix, see #1678 */
-			items[i].raw_data =
-				malloc(raw_data_length + 2);
-			if (items[i].raw_data == NULL) {
-				ERR_ALLOC_FAILED;
-				load_rdata_purge(rdata, items, i + 1, desc,
-				                 type);
-				return NULL;
-			}
-			items[i].raw_data[0] = raw_data_length;
-
-			if (!fread_wrapper(items[i].raw_data + 1,
-			                   sizeof(uint8_t),
-			      raw_data_length, f)) {
-				load_rdata_purge(rdata, items, i + 1, desc,
-				                 type);
-				dbg_zload("zload: load_rdata: Cannot read "
-				          "raw data.\n");
-				return NULL;
-			}
-			dbg_zload_detail("zload: load_rdata: Read raw_data "
-			                 "length=%d.\n",
-			                 raw_data_length);
-		}
+	rrset_list_t *tmp;
+	if (*head == NULL) {
+		return;
 	}
 
-	/* Each item has refcount already incremented for saving in rdata. */
-	int ret = knot_rdata_set_items(rdata, items, rdata_count);
-	if (ret != KNOT_EOK) {
-		dbg_zload("zload: read_rdata: Could not set items "
-		          "when loading rdata. Reason: %s\n.",
-		          knot_strerror(ret));
-		load_rdata_purge(rdata, items, desc->length, desc, type);
-		return NULL;
+	while (*head != NULL) {
+		tmp = *head;
+		*head = (*head)->next;
+		free(tmp);
 	}
 
-	free(items);
-	assert(rdata->count == rdata_count);
+	*head = NULL;
 	
-	dbg_zload_detail("zload: read_rdata: All %d items read "
-	                 "successfully.\n",
-	                 desc->length);
-
-	return rdata;
+	dbg_zp("zp: list_delete: List deleleted.\n");
 }
 
-/*!
- * \brief Loads RRSIG from binary file.
- *
- * \param f File to read from.
- *
- * \return pointer to created and read RRSIG on success, NULL otherwise.
- */
-static knot_rrset_t *knot_load_rrsig(void *f, knot_dname_t **id_array,
-                                         int use_ids)
+static int find_rrset_for_rrsig_in_node(knot_zone_contents_t *zone,
+                                 knot_node_t *node,
+                                 knot_rrset_t *rrsig)
 {
-	if (f == NULL || id_array == NULL) {
-		dbg_zload("zload: load_rrsig: Bad arguments.\n");
-		return NULL;
+	assert(node);
+
+	assert(knot_dname_compare(rrsig->owner, node->owner) == 0);
+
+	knot_rrset_t *tmp_rrset =
+		knot_node_get_rrset(node,
+	                            knot_rrset_rdata_rrsig_type_covered(rrsig));
+
+	int ret;
+
+	if (tmp_rrset == NULL) {
+		dbg_zp("zp: find_rr_for_sig_in_node: Node does not contain "
+		       "RRSet of type %d.\n",
+		       knot_rrset_rdata_rrsig_type_covered(rrsig));
+		tmp_rrset = knot_rrset_new(rrsig->owner,
+		                           knot_rrset_rdata_rrsig_type_covered(rrsig),
+		                           rrsig->rclass,
+		                           rrsig->ttl);
+		if (tmp_rrset == NULL) {
+			dbg_zp("zp: find_rr_for_sig_in_node: Cannot create "
+			       "dummy RRSet.\n");
+			return KNOT_ERROR;
+		}
+
+		ret = knot_zone_contents_add_rrset(zone, tmp_rrset, &node,
+		                                   KNOT_RRSET_DUPL_MERGE, 1);
+		assert(ret <= 0);
+		if (ret < 0) {
+			dbg_zp("zp: Failed to add new dummy RRSet to the zone."
+			       "\n");
+			return KNOT_ERROR;
+		}
 	}
 	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	if (use_ids) {
-		fread_wrapper = fread_safe_from_file;
-	} else {
-		fread_wrapper = read_from_stream;
-	}
+	assert(tmp_rrset);
 	
-	knot_rrset_t *rrsig = NULL;
-
-	uint16_t rrset_type = 0;
-	uint16_t rrset_class = 0;
-	uint32_t rrset_ttl = 0;
-
-	uint32_t rdata_count = 0;
-
-	if (!fread_wrapper(&rrset_type, sizeof(rrset_type), 1, f)) {
-		dbg_zload("zload: load_rrsig: Cannot read type.\n");
-		return NULL;
-	}
-
-	if (rrset_type != KNOT_RRTYPE_RRSIG) {
-		dbg_zload("zload: load_rrsig: RRSIG has wrong type,"
-		          " probably data corruption.\n");
-		return NULL;
-	}
-	dbg_zload_detail("zload: load_rrsig: RRSIG type: %d\n", rrset_type);
-	if (!fread_wrapper(&rrset_class, sizeof(rrset_class), 1, f)) {
-		dbg_zload("zload: load_rrsig: Cannot read class.\n");
-		return NULL;
+	if (tmp_rrset->ttl != rrsig->ttl) {
+		char *name = knot_dname_to_str(tmp_rrset->owner);
+		assert(name);
+		log_zone_warning("RRSIG owned by: %s cannot be added to "
+		                 "its RRSet, because their TTLs differ. "
+		                 "Changing TTL to value=%d.\n",
+		                 name, tmp_rrset->ttl);
+		free(name);
+	}
+
+	ret = knot_zone_contents_add_rrsigs(zone, rrsig, &tmp_rrset, &node,
+			                    KNOT_RRSET_DUPL_MERGE, 1);
+	if (ret < 0) {
+		dbg_zp("zp: find_rr_for_sig: Cannot add RRSIG.\n");
+		return KNOT_EINVAL;
+	} else if (ret > 0) {
+		knot_rrset_deep_free(&rrsig, 0, 0);
 	}
-	dbg_zload_detail("zload: load_rrsig: Class=%d\n", rrset_class);
+	
+	knot_dname_release(tmp_rrset->owner);
 
-	if (!fread_wrapper(&rrset_ttl, sizeof(rrset_ttl), 1, f)) {
-		dbg_zload("zload: load_rrsig: Cannot read TTL.\n");
-		return NULL;
-	}
-	dbg_zload_detail("zload: load_rrsig: TTL=%d\n", rrset_ttl);
+	assert(tmp_rrset->rrsigs != NULL);
 
-	if (!fread_wrapper(&rdata_count, sizeof(rdata_count), 1, f)) {
-		dbg_zload("zload: load_rrsig: Cannot read rdata count.\n");
-		return NULL;
-	}
+	return KNOT_EOK;
+}
 
-	rrsig = knot_rrset_new(NULL, rrset_type, rrset_class, rrset_ttl);
-	if (rrsig == NULL) {
-		dbg_zload("zload: load_rrsig: Cannot create new RRSIG.\n");
+static knot_node_t *create_node(knot_zone_contents_t *zone,
+	knot_rrset_t *current_rrset,
+	int (*node_add_func)(knot_zone_contents_t *zone, knot_node_t *node,
+	                     int create_parents, uint8_t, int),
+	knot_node_t *(*node_get_func)(const knot_zone_contents_t *zone,
+					const knot_dname_t *owner))
+{
+	dbg_zp_verb("zp: create_node: Creating node using RRSet: %p.\n",
+	            current_rrset);
+	knot_node_t *node =
+		knot_node_new(current_rrset->owner, NULL, 0);
+	if (node_add_func(zone, node, 1, 0, 1) != 0) {
 		return NULL;
 	}
+	
+	assert(current_rrset->owner == node->owner);
 
-	knot_rdata_t *tmp_rdata = NULL;
-
-	dbg_zload_detail("zload: load_rrsig: Loading %d rdata entries.\n",
-	                 rdata_count);
+	return node;
+}
 
-	for (int i = 0; i < rdata_count; i++) {
-		tmp_rdata = knot_load_rdata(KNOT_RRTYPE_RRSIG, f,
-					      id_array, use_ids);
-		if (tmp_rdata) {
-			int ret = knot_rrset_add_rdata(rrsig, tmp_rdata);
-			if (ret != KNOT_EOK) {
-				dbg_zload("zload: load_rrsig: Cannot "
-				          "add RDATA\n.");
-				knot_rrset_deep_free(&rrsig, 0, 1, 1);
-				return NULL;
-			}
-		} else {
-			dbg_zload("zload: load_rrsig: Cannot load rdata.\n");
-			knot_rrset_deep_free(&rrsig, 0, 1, 1);
-			return NULL;
+static void process_rrsigs_in_node(parser_context_t *parser,
+                                   knot_zone_contents_t *zone,
+                                   knot_node_t *node)
+{
+	dbg_zp_verb("zp: process_rrsigs: Processing RRSIGS in node: %p.\n",
+	            node);
+	rrset_list_t *tmp = parser->node_rrsigs;
+	while (tmp != NULL) {
+		if (find_rrset_for_rrsig_in_node(zone, node,
+						 tmp->data) != KNOT_EOK) {
+			fprintf(stderr, "Could not add RRSIG to zone!\n");
+			return;
 		}
+		tmp = tmp->next;
 	}
-
-	dbg_zload_detail("zload: load_rrsig: RRSIG loaded successfully.\n");
-	return rrsig;
 }
 
-/*!
- * \brief Loads RRSet from binary file.
- *
- * \param f File to read from.
- *
- * \return pointer to created and read RRSet on success, NULL otherwise.
- */
-static knot_rrset_t *knot_load_rrset(void *f, knot_dname_t **id_array,
-                                         int use_ids)
+static void process_error(const scanner_t *s)
 {
-	if (f == NULL) {
-		dbg_zload("zload: load_rrset: NULL arguments.\n");
-		return NULL;
-	}
-	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	if (use_ids) {
-		fread_wrapper = fread_safe_from_file;
+	err_count++;
+	if (s->stop == true) {
+		printf("ERROR=%s\n", knot_strerror(s->error_code));
 	} else {
-		fread_wrapper = read_from_stream;
-	}
-	
-	knot_rrset_t *rrset = NULL;
-
-	uint16_t rrset_type = 0;
-	uint16_t rrset_class = 0;
-	uint32_t rrset_ttl = 0;
-
-	uint32_t rdata_count = 0;
-	uint8_t rrsig_count = 0;
-
-	knot_dname_t *owner = NULL;
-
-	if (!use_ids) {
-		dbg_zload_detail("zload: load_rrset: "
-		                 "Loading owner of new RRSet from wire.\n");
-		owner = read_dname_with_id(f, use_ids);
-		if (owner == NULL) {
-			dbg_zload("zload: load_rrset: Cannot load owner.\n");
-			return NULL;
-		}
+		printf("WARNG=%s\n", knot_strerror(s->error_code));
 	}
+	fflush(stdout);
+}
 
-	if (!fread_wrapper(&rrset_type, sizeof(rrset_type), 1, f)) {
-		dbg_zload("zload: load_rrset: Cannot load RRSet type.\n");
-		if (!use_ids) {
-			knot_dname_free(&owner);
+// TODO this could be a part of the cycle below, but we'd need a buffer.
+static size_t calculate_item_size(const knot_rrset_t *rrset,
+                               const scanner_t *scanner)
+{
+	const rdata_descriptor_t *desc = get_rdata_descriptor(rrset->type);
+	assert(desc);
+	size_t size = 0;
+	for (int i = 0; desc->block_types[i] != KNOT_RDATA_WF_END; i++) {
+		int item = desc->block_types[i];
+		if (descriptor_item_is_dname(item)) {
+			size += sizeof(knot_dname_t *);
+		} else if (descriptor_item_is_fixed(item)) {
+			assert(item == scanner->r_data_blocks[i + 1] -
+			       scanner->r_data_blocks[i]);
+			size += item;
+		} else if (descriptor_item_is_remainder(item)) {
+			size += scanner->r_data_blocks[i + 1] -
+			        scanner->r_data_blocks[i];
+		} else {
+			//naptr
+			assert(0);
 		}
-		return NULL;
 	}
 	
-	dbg_zload_detail("zload: load_rrset: Type=%u\n", rrset_type);
-	if (!fread_wrapper(&rrset_class, sizeof(rrset_class), 1, f)) {
-		dbg_zload("zload: load_rrset: Cannot load RRSet class.\n");
-		if (!use_ids) {
-			knot_dname_free(&owner);
-		}
-		return NULL;
-	}
-	dbg_zload_detail("zload: load_rrset: Class=%u\n", rrset_class);
-	if (!fread_wrapper(&rrset_ttl, sizeof(rrset_ttl), 1, f)) {
-		dbg_zload("zload: load_rrset: Cannot load RRSet TTL.\n");
-		if (!use_ids) {
-			knot_dname_free(&owner);
-		}
-		return NULL;
-	}
-	dbg_zload_detail("zload: load_rrset: TTL=%u\n", rrset_ttl);
-	if (!fread_wrapper(&rdata_count, sizeof(rdata_count), 1, f)) {
-		if (!use_ids) {
-			knot_dname_free(&owner);
-		}
-		return NULL;
-	}
-	dbg_zload_detail("zload: load_rrset: rdata count=%u\n", rdata_count);
-	if (!fread_wrapper(&rrsig_count, sizeof(rrsig_count), 1, f)) {
-		if (!use_ids) {
-			knot_dname_free(&owner);
-		}
-		return NULL;
-	}
-	dbg_zload_detail("zload: load_rrset: RRSIG count=%u\n", rrsig_count);
-
-dbg_zload_exec_detail(
-	char *name = knot_dname_to_str(owner);
-	dbg_zload_detail("zload: load_rrset: Loading RRSet owned by: %s.\n",
-	          name);
-	free(name);
-);
+	return size;
+}
 
-	rrset = knot_rrset_new(owner, rrset_type, rrset_class, rrset_ttl);
+static int add_rdata_to_rr(knot_rrset_t *rrset, const scanner_t *scanner)
+{
 	if (rrset == NULL) {
-		dbg_zload("zload: load_rrset: Could not create rrset.");
-		knot_dname_free(&owner);
-		return NULL;
+		dbg_zp("zp: add_rdata_to_rr: No RRSet.\n");
+		return KNOT_EINVAL;
 	}
-
-	if (!use_ids) {
-		/* Directly release if allocated locally. */
-		knot_dname_release(owner);
-		owner = NULL;
+	
+	const rdata_descriptor_t *desc =
+		get_rdata_descriptor(knot_rrset_type(rrset));
+	assert(desc);
+	
+	dbg_zp_detail("zp: add_rdata_to_rr: Adding type %d, RRSet has %d RRs.\n",
+	              rrset->type, rrset->rdata_count);
+	
+	size_t rdlen = calculate_item_size(rrset, scanner);
+	size_t offset = 0;
+	uint8_t *rdata = knot_rrset_create_rdata(rrset, rdlen);
+	if (rdata == NULL) {
+		dbg_zp("zp: create_rdata: Could not create RR.\n");
+		return KNOT_ENOMEM;
 	}
-
-	dbg_zload_detail("zload: load_rrset: RRSet type=%d\n", rrset->type);
-
-	knot_rdata_t *tmp_rdata = NULL;
-
-	for (int i = 0; i < rdata_count; i++) {
-		tmp_rdata = knot_load_rdata(rrset->type, f,
-					      id_array, use_ids);
-		if (tmp_rdata) {
-			int ret = knot_rrset_add_rdata(rrset, tmp_rdata);
-			if (ret != KNOT_EOK) {
-				dbg_zload("zload: load_rrset: Cannot add "
-				          "RDATA.\n");
-				knot_rrset_deep_free(&rrset, 0, 1, 1);
-				return NULL;
+	
+	for (int i = 0; desc->block_types[i] != KNOT_RDATA_WF_END; i++) {
+		int item = desc->block_types[i];
+		if (descriptor_item_is_dname(item)) {
+			/* TODO another function perhaps? */
+			knot_dname_t *dname =
+				knot_dname_new_from_wire(scanner->r_data +
+			                                 scanner->r_data_blocks[i],
+			                                 scanner->r_data_blocks[i + 1] - scanner->r_data_blocks[i],
+			                                 NULL);
+			if (dname == NULL) {
+				//TODO handle
+				return KNOT_ERROR;
 			}
+dbg_zp_exec_detail(
+			char *name = knot_dname_to_str(dname);
+			dbg_zp_detail("zp: arr_rdata_to_rr: "
+			              "Offset=%d:Adding dname=%s (%p)\n",
+			              offset, name, dname);
+			free(name);
+);
+			memcpy(rdata + offset, &dname, sizeof(knot_dname_t *));
+			offset += sizeof(knot_dname_t *);
+			//parse dname from binary
+		} else if (descriptor_item_is_fixed(item)) {
+			//copy the whole thing
+			// TODO check the size
+			assert(item == scanner->r_data_blocks[i + 1] -
+			       scanner->r_data_blocks[i]);
+			memcpy(rdata + offset,
+			       scanner->r_data + scanner->r_data_blocks[i],
+			       item);
+			offset += item;
+		} else if (descriptor_item_is_remainder(item)) {
+			//copy the rest
+			memcpy(rdata + offset,
+			       scanner->r_data + scanner->r_data_blocks[i],
+			       scanner->r_data_blocks[i + 1] -
+			       scanner->r_data_blocks[i]);
+			offset += scanner->r_data_blocks[i + 1] -
+			          scanner->r_data_blocks[i];
 		} else {
-			dbg_zload("zload: load_rrset: Cannot load rdata.\n");
-			knot_rrset_deep_free(&rrset, 0, 1, 1);
-			return NULL;
-		}
-	}
-
-	knot_rrset_t *tmp_rrsig = NULL;
-
-	dbg_zload_detail("zload: load_rrset: Reading: %d RRSIGs.\n",
-	                 rrsig_count);
-	if (rrsig_count) {
-		tmp_rrsig = knot_load_rrsig(f, id_array, use_ids);
-		if (tmp_rrsig == NULL) {
-			dbg_zload("zload: load_rrset: Cannot load RRSIG.\n");
-			knot_rrset_deep_free(&rrset, 0, 1, 1);
-			return NULL;
-		}
-		if (!use_ids) {
-			knot_rrset_set_owner(tmp_rrsig, rrset->owner);
+			//NAPTR
+			assert(knot_rrset_type(rrset) == KNOT_RRTYPE_NAPTR);
+			assert(0);
 		}
 	}
-
-	knot_rrset_set_rrsigs(rrset, tmp_rrsig);
-
-	dbg_zload_detail("zload: load_rrset: Finished loading RRSet %p.\n",
-	                 rrset);
-	return rrset;
+	
+	return KNOT_EOK;
 }
 
-/*!
- * \brief Loads node from binary file.
- *
- * \param f File to read from.
- *
- * \return Pointer to created and read node on success, NULL otherwise.
- */
-static knot_node_t *knot_load_node(FILE *f, knot_dname_t **id_array)
+static void process_rr(const scanner_t *scanner)
 {
-	if (f == NULL || id_array == NULL) {
-		dbg_zload("zload: load_node: Wrong parameters.\n");
-		return NULL;
+	dbg_zp_detail("Owner from parser=%s\n",
+	              scanner->r_owner);
+	rr_count++;
+	char add = 0;
+	parser_context_t *parser = scanner->data;
+	knot_zone_contents_t *contents = parser->current_zone;
+	/* Create rrset. TODO will not be always needed. */
+	knot_dname_t *current_owner = NULL;
+	knot_rrset_t *current_rrset = NULL;
+	if (parser->last_node &&
+	    (scanner->r_owner_length == parser->last_node->owner->size) &&
+	    (strncmp((char *)parser->last_node->owner->name,
+	            (char *)scanner->r_owner, scanner->r_owner_length) == 0)) {
+		// no need to create new dname;
+		current_owner = parser->last_node->owner;
+		// what about RRSet, do we need a new one?
+		current_rrset = knot_node_get_rrset(parser->last_node,
+		                                    scanner->r_type);
+		if (current_rrset == NULL) {
+			add = 1;
+			new_rr_count++	;
+			current_rrset =
+				knot_rrset_new(current_owner,
+				               scanner->r_type,
+				               scanner->r_class,
+				               scanner->r_ttl);
+		}
+	} else {
+		add = 1;
+//		if (strncmp((char *)parser->last_node->owner->name,
+//	                (char *)scanner->r_owner, scanner->r_owner_length)) {
+//			new_dname_count++;
+//			current_owner = 
+//		                knot_dname_new_from_wire(scanner->r_owner,
+//	                                         scanner->r_owner_length,
+//	                                         NULL);
+//		} else {
+//			current_owner = parser->last_node->owner;
+//		}
+		current_owner = 
+			knot_dname_new_from_wire(scanner->r_owner,
+			                         scanner->r_owner_length,
+			                         NULL);
+		new_rr_count++;
+		new_dname_count++;
+		current_rrset =
+			knot_rrset_new(current_owner,
+			               scanner->r_type,
+			               scanner->r_class,
+			               scanner->r_ttl);
+		knot_dname_release(current_owner);
 	}
 	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	fread_wrapper = fread_safe_from_file;
+	assert(current_owner);
+	parser->current_rrset = current_rrset;
+	assert(current_rrset);
 	
-	uint8_t flags = 0;
-	knot_node_t *node = NULL;
-	uint32_t parent_id = 0;
-	uint32_t nsec3_node_id = 0;
-	uint16_t rrset_count = 0;
-	uint32_t dname_id = 0;
+	int ret = add_rdata_to_rr(current_rrset, scanner);
+	assert(ret == 0);
+	
+	dbg_zp_verb("zp: process_rr: Processing type: %s.\n",
+	            knot_rrtype_to_string(parser->current_rrset->type));
+	dbg_zp_verb("zp: process_rr: RDATA count: %d.\n",\
+	            parser->current_rrset->rdata->count);
 
-	/* At the beginning of node - just dname_id !!!.*/
-	if (!fread_wrapper(&dname_id, sizeof(dname_id), 1, f)) {
-		dbg_zload("zload: load_node: Cannot read owner ID.\n");
-		return NULL;
-	}
+	assert(current_rrset->rdata_count);
 
-	if (!fread_wrapper(&parent_id, sizeof(parent_id), 1, f)) {
-		dbg_zload("zload: load_node: Cannot read owner ID.\n");
-		return NULL;
-	}
+	int (*node_add_func)(knot_zone_contents_t *, knot_node_t *, int,
+	                     uint8_t, int);
+	knot_node_t *(*node_get_func)(const knot_zone_contents_t *,
+	                                const knot_dname_t *);
 
-	if (!fread_wrapper(&flags, sizeof(flags), 1, f)) {
-		dbg_zload("zload: load_node: Cannot read node flags.\n");
-		return NULL;
-	}
 
-	if (!fread_wrapper(&nsec3_node_id, sizeof(nsec3_node_id), 1, f)) {
-		dbg_zload("zload: load_node: Cannot read NSEC3 node.\n");
-		return NULL;
-	}
+	/* If we have RRSIG of NSEC3 type first node will have
+	 * to be created in NSEC3 part of the zone */
 
-	if (!fread_wrapper(&rrset_count, sizeof(rrset_count), 1, f)) {
-		dbg_zload("zload: load_node: Cannot read rrset count.\n");
-		return NULL;
-	}
-	knot_dname_t *owner = id_array[dname_id];
-	if (owner == NULL) {
-		dbg_zload("zload: load_node: Wrong dname ID, cannot load.\n");
-		return NULL;
+	uint16_t type_covered = 0;
+	if (current_rrset->type == KNOT_RRTYPE_RRSIG) {
+		type_covered =
+			knot_rrset_rdata_rrsig_type_covered(current_rrset);
 	}
 
-	dbg_zload_detail("zload: load_node: Node owner id: %d.\n", dname_id);
-dbg_zload_exec_detail(
-	char *name = knot_dname_to_str(owner);
-	dbg_zload_detail("zload: load_node: Node owned by: %s.\n", name);
-	free(name);
-);
-	dbg_zload_detail("zload: load_node: Number of RRSets in a node: %d.\n",
-	                 rrset_count);
-
-	node = owner->node;
-
-	if (node == NULL) {
-		dbg_zload("zload: load_node: NULL node, cannot proceed.\n");
-		return NULL;
-	}
-	/* XXX can it be 0, ever? I think not. */
-	if (nsec3_node_id != 0) {
-		knot_node_set_nsec3_node(node, id_array[nsec3_node_id]->node);
+	if (current_rrset->type != KNOT_RRTYPE_NSEC3 &&
+	    type_covered != KNOT_RRTYPE_NSEC3) {
+		node_add_func = &knot_zone_contents_add_node;
+		node_get_func = &knot_zone_contents_get_node;
 	} else {
-		knot_node_set_nsec3_node(node, NULL);
+		node_add_func = &knot_zone_contents_add_nsec3_node;
+		node_get_func = &knot_zone_contents_get_nsec3_node;
+	}
+
+	if (current_rrset->type == KNOT_RRTYPE_SOA) {
+		if (knot_node_rrset(knot_zone_contents_apex(contents),
+		                      KNOT_RRTYPE_SOA) != NULL) {
+			/* Receiving another SOA. */
+			if (!knot_rrset_equal(current_rrset,
+			    knot_node_rrset(knot_zone_contents_apex(contents),
+			    KNOT_RRTYPE_SOA), KNOT_RRSET_COMPARE_WHOLE)) {
+				log_zone_error("Extra SOA record in the "
+				               "zone.\n");
+				/*!< \todo consider a new error */
+				parser->ret = KNOT_EBADZONE;
+				return;
+			} else {
+				log_zone_warning("encountered identical "
+				                 "extra SOA record");
+				parser->ret = KNOT_EOK;
+				return;
+			}
+		}
 	}
 
-	/* Retain new owner while releasing replaced owner. */
-	knot_node_set_owner(node, owner);
-	node->flags = flags;
-
-	//XXX will have to be set already...canonical order should do it
+	/*!< \todo Make sure the maximum RDLENGTH does not exceed 65535 bytes.*/
 
-	if (parent_id != 0) {
-		knot_node_set_parent(node, id_array[parent_id]->node);
-		assert(knot_node_parent(node) != NULL);
-	} else {
-		knot_node_set_parent(node, NULL);
+	if (current_rrset->type == KNOT_RRTYPE_SOA) {
+		if (knot_dname_compare(current_rrset->owner,
+					parser->origin_from_config) != 0) {
+			log_zone_error("SOA record has a different "
+				"owner than the one specified "
+				"in config! \n");
+			/* Such SOA cannot even be added, because
+			 * it would not be in the zone apex. */
+			/*!< \todo consider a new error */
+			parser->ret = KNOT_EBADZONE;
+			return;
+		}
 	}
 
-	knot_rrset_t *tmp_rrset = NULL;
+	if (current_rrset->type == KNOT_RRTYPE_RRSIG) {
+		knot_rrset_t *tmp_rrsig = current_rrset;
 
-	for (int i = 0; i < rrset_count; i++) {
-		if ((tmp_rrset = knot_load_rrset(f, id_array, 1)) == NULL) {
-			knot_node_free(&node);
-			/*!< \todo #1686 
-			 * Refactor freeing, might not be enough.
+		if (parser->last_node &&
+		    knot_dname_compare(parser->last_node->owner,
+		                         current_rrset->owner) != 0) {
+			/* RRSIG is first in the node, so we have to create it
+			 * before we return
 			 */
-			dbg_zload("zload: load_node: Cannot load RRSet.\n");
-			return NULL;
-		}
-		/* Retain new owner while releasing replaced owner. */
-		knot_rrset_set_owner(tmp_rrset, node->owner);
-		if (tmp_rrset->rrsigs != NULL) {
-			knot_rrset_set_owner(tmp_rrset->rrsigs, node->owner);
-		}
-		if (knot_node_add_rrset(node, tmp_rrset, 0) < 0) {
-			dbg_zload("zload: load_node: Cannot add RRSet "
-			          "to node.\n");
-			return NULL;
+			if (parser->node_rrsigs != NULL) {
+				process_rrsigs_in_node(parser,
+				                       contents,
+				                       parser->last_node);
+				rrset_list_delete(&parser->node_rrsigs);
+			}
+			
+			/* The node might however been created previously. */
+			parser->last_node =
+				knot_zone_contents_get_node(contents,
+					knot_rrset_owner(current_rrset));
+			
+			if (parser->last_node == NULL) {
+				/* Try NSEC3 tree. */
+				if (current_rrset->type == KNOT_RRTYPE_NSEC3 ||
+				    current_rrset->type == KNOT_RRTYPE_RRSIG) {
+					parser->last_node =
+						knot_zone_contents_get_nsec3_node(
+							contents,
+							knot_rrset_owner(
+								current_rrset));
+				}
+			}
+			
+			if (parser->last_node == NULL) {
+				/* Still NULL, node has to be created. */
+				if ((parser->last_node = create_node(contents,
+				                                     current_rrset, node_add_func,
+				                                     node_get_func)) == NULL) {
+					knot_rrset_free(&tmp_rrsig);
+					dbg_zp("zp: process_rr: Cannot "
+					       "create new node.\n");
+					log_zone_error("None cannot be created.\n");
+					/*!< \todo consider a new error */
+					parser->ret = KNOT_ERROR;
+					return;
+				}
+			}
 		}
-	}
-	assert(node != NULL);
-	dbg_zload_detail("zload: load_node: Node loaded: %p\n", node);
-	return node;
-}
 
-/*!
- * \brief Finds and sets wildcard child for given node's owner.
- *
- * \param zone Current zone.
- * \param node Node to be used.
- * \param nsec3 Is NSEC3 node.
- */
-static void find_and_set_wildcard_child(knot_zone_contents_t *zone,
-				 knot_node_t *node, int nsec3)
-{
-	if (zone == NULL || node == NULL) {
-		dbg_zload("zload: set_wc: Bad arguments.\n");
+		if (rrset_list_add(&parser->node_rrsigs, tmp_rrsig) != 0) {
+			dbg_zp("zp: process_rr: Cannot "
+			       "create new node.\n");
+			parser->ret = KNOT_ERROR;
+			return;
+		}
+		
+		dbg_zp_verb("zp: process_rr: RRSIG proccesed successfully.\n");
+		parser->ret = KNOT_EOK;
 		return;
 	}
-	knot_dname_t *chopped = knot_dname_left_chop(node->owner);
-	knot_node_t *wildcard_parent;
-	if (!nsec3) {
-		wildcard_parent =
-			knot_zone_contents_get_node(zone, chopped);
-	} else {
-		wildcard_parent =
-			knot_zone_contents_get_nsec3_node(zone, chopped);
-	}
-
-	/* Directly discard. */
-	knot_dname_free(&chopped);
-
-	assert(wildcard_parent); /* it *has* to be there */
+	
+	/*! \todo Move RRSIG and RRSet handling to funtions. */
+	assert(current_rrset->type != KNOT_RRTYPE_RRSIG);
 
-	knot_node_set_wildcard_child(wildcard_parent, node);
-}
+	knot_node_t *node = NULL;
+	/* \note this could probably be much simpler */
+	if (parser->last_node && current_rrset->type != KNOT_RRTYPE_SOA &&
+	    knot_dname_compare(parser->last_node->owner,
+				 current_rrset->owner) ==
+	    0) {
+		node = parser->last_node;
+	} else {
+		if (parser->last_node && parser->node_rrsigs) {
+			process_rrsigs_in_node(parser,
+			                       contents,
+			                       parser->last_node);
+		}
 
-/*!
- * \brief Checks if magic string at the beginning of the file is the same
- *        as defined.
- *
- * \param f File to read magic string from.
- * \param MAGIC Magic string.
- * \param MAGIC_LENGTH Length of magic string.
- *
- * \retval 1 if magic is the same.
- * \retval 0 otherwise.
- */
-static int knot_check_magic(FILE *f, const uint8_t* MAGIC, uint MAGIC_LENGTH)
-{
-	uint8_t tmp_magic[MAGIC_LENGTH];
-	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	fread_wrapper = fread_safe_from_file;
+		rrset_list_delete(&parser->node_rrsigs);
 
-	if (!fread_wrapper(&tmp_magic, sizeof(uint8_t), MAGIC_LENGTH, f)) {
-		return 0;
+		/* new node */
+		node = node_get_func(contents, current_rrset->owner);
 	}
 
-	for (int i = 0; i < MAGIC_LENGTH; i++) {
-		if (tmp_magic[i] != MAGIC[i]) {
-			return 0;
+	if (node == NULL) {
+		if (parser->last_node && parser->node_rrsigs) {
+			process_rrsigs_in_node(parser,
+			                       contents,
+			                       parser->last_node);
 		}
-	}
 
-	return 1;
-}
-
-static unsigned long calculate_crc(FILE *f)
-{
-	crc_t crc = crc_init();
-	/* Get file size. */
-	fseek(f, 0L, SEEK_END);
-	size_t file_size = ftell(f);
-	fseek(f, 0L, SEEK_SET);
-	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	fread_wrapper = fread_safe_from_file;
-
-	const size_t chunk_size = 4096;
-	/* read chunks of 4 kB */
-	size_t read_bytes = 0;
-	/* Prealocate chunk */
-	unsigned char *chunk = malloc(sizeof(unsigned char) * chunk_size);
-	CHECK_ALLOC_LOG(chunk, 0);
-	while ((file_size - read_bytes) > chunk_size) {
-		if (!fread_wrapper(chunk,
-		                   sizeof(unsigned char), chunk_size, f)) {
-			dbg_zload("zload: calculate_crc: Failed to read "
-			          "data chunk.\n");
-			free(chunk);
-			return 0;
+		if ((node = create_node(contents, current_rrset,
+					node_add_func,
+					node_get_func)) == NULL) {
+			dbg_zp("zp: process_rr: Cannot "
+			       "create new node.\n");
+			/*!< \todo consider a new error */
+			log_zone_error("Cannot create new node.\n");
+			parser->ret = KNOT_ERROR;
+			return;
 		}
-		crc = crc_update(crc, chunk,
-		                 sizeof(unsigned char) * chunk_size);
-		read_bytes += chunk_size;
 	}
-
-	/* Read the rest of the file */
-	if (!fread_wrapper(chunk, sizeof(unsigned char), file_size - read_bytes,
-	                f)) {
-		dbg_zload("zload: calculate_crc: Failed to read "
-		          "data remainder.\n");
-		free(chunk);
-		return 0;
+	
+//	rrset = knot_node_get_rrset(node, current_rrset->type);
+//	if (!rrset) {
+//		rrset = current_rrset;
+//	} else {
+//		merged = 1;
+//	}
+///	if (!rrset) {
+//		int ret = knot_rrset_deep_copy(current_rrset, &rrset, 1);
+//		if (ret != KNOT_EOK) {
+//			dbg_zp("zp: Cannot copy RRSet.\n");
+//			return ret;
+//		}
+//		rrset = knot_rrset_new(current_rrset->owner,
+//					 current_rrset->type,
+//					 current_rrset->rclass,
+//					 current_rrset->ttl);
+//		if (rrset == NULL) {
+//			dbg_zp("zp: process_rr: Cannot "
+//			       "create new RRSet.\n");
+//			return KNOTDZCOMPILE_ENOMEM;
+//		}
+
+//		if (knot_rrset_add_rdata(rrset, current_rrset->rdata) != 0) {
+//			knot_rrset_free(&rrset);
+//			dbg_zp("zp: process_rr: Cannot "
+//			       "add RDATA to RRSet.\n");
+//			return KNOTDZCOMPILE_EBRDATA;
+//		}
+		
+		/* Selected merge option does not really matter here. */
+//		if (knot_zone_contents_add_rrset(contents, current_rrset, &node,
+//		                   KNOT_RRSET_DUPL_MERGE, 1) < 0) {
+//			knot_rrset_free(&rrset);
+//			dbg_zp("zp: process_rr: Cannot "
+//			       "add RDATA to RRSet.\n");
+//			return KNOTDZCOMPILE_EBRDATA;
+//		}
+//	} else {
+//	TODO needs solving
+//	if (current_rrset->type !=
+//			KNOT_RRTYPE_RRSIG && rrset->ttl !=
+//			current_rrset->ttl) {
+//		fprintf(stderr, 
+//			"TTL does not match the TTL of the RRSet. "
+//			"Changing to %d.\n", rrset->ttl);
+//	}
+
+	if (add) {
+		ret = knot_zone_contents_add_rrset(contents, current_rrset,
+		                                   &node,
+		                                   KNOT_RRSET_DUPL_MERGE, 1);
+		if (ret < 0) {
+			dbg_zp("zp: process_rr: Cannot "
+			       "add RRSets.\n");
+			/*!< \todo mixed error codes, has to be changed. */
+			parser->ret = ret;
+			return;
+		} else if (ret > 0) {
+			knot_rrset_deep_free(&current_rrset, 0, 0);
+		}
 	}
+//	}
 
-	crc = crc_update(crc, chunk,
-	                 sizeof(unsigned char) * (file_size - read_bytes));
-	free(chunk);
-
-	fseek(f, 0L, SEEK_SET);
-	return (unsigned long)crc_finalize(crc);
+	parser->last_node = node;
+	
+	dbg_zp_verb("zp: process_rr: RRSet %p processed successfully.\n",
+	            parser->current_rrset);
+	parser->ret = KNOT_EOK;
 }
 
-int knot_zload_open(zloader_t **dst, const char *filename)
+int knot_zload_open(zloader_t **dst, const char *source, const char *origin, 
+                    int semantic_checks)
 {
-	char crc_buf[65];
-
-	if (!dst || !filename) {
+	if (!dst || !source || !origin) {
 		dbg_zload("zload: open: Bad arguments.\n");
 		return KNOT_EINVAL;
 	}
 	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	fread_wrapper = fread_safe_from_file;
-
-	*dst = 0;
-
-	/* Open file for binary read. */
-	FILE *f = fopen(filename, "rb");
-	if (knot_unlikely(!f)) {
-		int reason = errno;
-		dbg_zload("knot_zload_open: failed to open '%s'\n",
-		          filename);
-		switch (reason) {
-		case EACCES: return KNOT_EACCES; break;
-		case ENOENT: return KNOT_ENOENT; break;
-		case ENOMEM: return KNOT_ENOMEM; break;
-		default: break;
-		}
-
-		return KNOT_EFEWDATA; // No such file or directory (POSIX.1)
-	}
+	*dst = NULL;
+	/* Create context. */
+	parser_context_t *context = xmalloc(sizeof(parser_context_t));
+	context->origin_from_config = knot_dname_new_from_str(origin,
+	                                                       strnlen((char *)origin,
+	                                                               255),
+	                                                       NULL);
+	assert(context->origin_from_config);
+	context->last_node = knot_node_new(context->origin_from_config,
+	                                    NULL, 0);
+	knot_zone_t *zone = knot_zone_new(context->last_node, 0, 0);
+	context->current_zone = knot_zone_get_contents(zone);
+	context->node_rrsigs = NULL;
 	
-	/* Calculate file size. */
-	fseek(f, 0L, SEEK_END);
-	size_t file_size = ftell(f);
-	fseek(f, 0L, SEEK_SET);
-	if (file_size < MAGIC_LENGTH) {
-		fclose(f);
-		return KNOT_EFEWDATA;
-	}
-
-	/* Calculate CRC and compare with filename.crc file */
-	unsigned long crc_calculated = calculate_crc(f);
-
-	/* Read CRC from filename.crc file */
-	char *crc_path =
-		malloc(sizeof(char) *
-	               (strlen(filename) + 4 /* strlen(".crc") */ + 1));
-	if (knot_unlikely(!crc_path)) {
-		fclose(f);
-		ERR_ALLOC_FAILED;
-		return KNOT_ENOMEM;
-	}
-	memcpy(crc_path, filename, strlen(filename));
-	memcpy(crc_path + strlen(filename), ".crc", 4);
-	crc_path[strlen(filename) + 4] = '\0';
-
-	int f_crc = open(crc_path, O_RDONLY);
-	if (f_crc == -1) {
-		/* FIXME: Print strerror_r(errno) in dbg message */
-		dbg_zload("knot_zload_open: failed to open '%s'\n",
-			  crc_path);
-		free(crc_path);
-		fclose(f);
-		return KNOT_ECRC;
-	}
-
-	ssize_t crc_read_bytes = 0;
-	crc_read_bytes = read(f_crc, crc_buf, 64);
-	if (crc_read_bytes == -1) {
-		/* FIXME: Print strerror_r(errno) in dbg message */
-		dbg_zload("knot_zload_open: could not read "
-		                   "CRC from file '%s'\n",
-		                   crc_path);
-		free(crc_path);
-		close(f_crc);
-		fclose(f);
-		return KNOT_ECRC;
-	}
-	crc_buf[crc_read_bytes] = '\0';
-
-	unsigned long crc_from_file = 0;
-	errno = 0;
-	crc_from_file = strtoul(crc_buf, (char **) NULL, 10);
-	if (errno != 0) {
-		/* FIXME: Print strerror_r(errno) in dbg message */
-		dbg_zload("knot_zload_open: could not convert "
-		                   "CRC from file '%s'\n",
-		                   crc_path);
-		close(f_crc);
-		fclose(f);
-		free(crc_path);
-		return KNOT_ERROR;
-	}
-
-	/* Free some value and close the CRC file */
-	free(crc_path);
-	close(f_crc);
-	
-	/* Check magic sequence. */
-	static const uint8_t MAGIC[MAGIC_LENGTH] = MAGIC_BYTES;
-	if (!knot_check_magic(f, MAGIC, MAGIC_LENGTH)) {
-		fclose(f);
-		dbg_zload("knot_zload_open: magic bytes "
-				   "in don't match '%*s' "
-			 "(%s)\n",
-			 (int)MAGIC_LENGTH, (const char*)MAGIC, filename);
-		return KNOT_EMALF; // Illegal byte sequence (POSIX.1, C99)
-	}
-
-	/* Compare calculated and read CRCs. */
-	if (crc_from_file != crc_calculated) {
-		dbg_zload("knot_zload_open: CRC failed for "
-		                   "file '%s'\n",
-		                   filename);
-		fclose(f);
-		return KNOT_ECRC;
-	}
-
-	/* Read source file length. */
-	uint32_t sflen = 0;
-	if (!fread_wrapper(&sflen, 1, sizeof(uint32_t), f)) {
-		dbg_zload("knot_zload_open: failed to read "
-				   "sfile length\n");
-		fclose(f);
-		return KNOT_ERROR;
-	}
-
-	/* Read source file. */
-	char *sfile = malloc(sflen);
-	if (!sfile) {
-		dbg_zload("knot_zload_open: invalid sfile "
-				   "length %u\n", sflen);
-		fclose(f);
-		return KNOT_ENOMEM;
-	}
-	if (!fread_wrapper(sfile, 1, sflen, f)) {
-		dbg_zload("knot_zload_open: failed to read %uB "
-				   "source file\n",
-			 sflen);
-		free(sfile);
-		fclose(f);
+	/* Create file loader. */
+	file_loader_t *loader = file_loader_create(source, origin,
+	                                           KNOT_CLASS_IN, 3600,
+	                                           process_rr,
+	                                           process_error,
+	                                           context);
+	if (loader == NULL) {
+		dbg_zload("Could not create file loader.\n");
 		return KNOT_ERROR;
 	}
 
 	/* Allocate new loader. */
-	zloader_t *zl = malloc(sizeof(zloader_t));
-	if (!zl) {
-		free(sfile);
-		fclose(f);
-		return KNOT_ENOMEM;
-	}
-
-	dbg_zload("knot_zload_open: opened '%s' as fp %p "
-			   "(source is '%s')\n",
-		 filename, f, sfile);
-	zl->filename = strdup(filename);
-	zl->source = sfile;
-	zl->fp = f;
+	zloader_t *zl = xmalloc(sizeof(zloader_t));
+	
+	zl->source = strdup(source);
+	zl->origin = strdup(origin);
+	zl->file_loader = loader;
 	*dst = zl;
 
 	return KNOT_EOK;
 }
 
-static void cleanup_id_array(knot_dname_t **id_array,
-			     const uint from, const uint to)
-{
-	if (id_array == NULL) {
-		dbg_zload("zload: cleanup_id_array: NULL arguments.\n");
-		return;
-	}
-	
-	for (uint i = from; i < to; i++) {
-		if (id_array[i] != NULL) {
-			knot_dname_release(id_array[i]);
-		}
-	}
-
-	free(id_array);
-}
-
-static knot_dname_table_t *create_dname_table_from_array(
-	knot_dname_t **array, uint max_id)
-{
-	if (array == NULL) {
-		/* should I set errno or what ... ? */
-		dbg_zload("zload: create_dname_table: No array passed.\n");
-		return NULL;
-	}
-
-	assert(array[0] == NULL);
-
-	knot_dname_table_t *ret = knot_dname_table_new();
-	CHECK_ALLOC_LOG(ret, NULL);
-
-	/* Table will have max_id entries */
-	for (uint i = 1; i < max_id; i++) {
-		assert(array[i]);
-		if (knot_dname_table_add_dname(ret,
-						 array[i]) != KNOT_EOK) {
-dbg_zload_exec_detail(
-			char *name = knot_dname_to_str(array[i]);
-			dbg_zload_detail("zload: create_dname_table: "
-			                 "Could not add dname: %s.\n",
-			                 name);
-			free(name);
-);
-			dbg_zload("zload: create_dname_table: "
-			          "Could not add dname.\n");
-			knot_dname_table_deep_free(&ret);
-			return NULL;
-		}
-	}
-
-	dbg_zload("zload: create_dname_table: Table loaded.\n");
-	return ret;
-}
-
-static knot_dname_t **create_dname_array(FILE *f, uint max_id)
-{
-	if (f == NULL) {
-		dbg_zload("zload: create_dname_array: Wrong arguments.\n");
-		return NULL;
-	}
-
-	knot_dname_t **array =
-		malloc(sizeof(knot_dname_t *) * ( max_id + 1));
-	if (array == NULL) {
-		ERR_ALLOC_FAILED;
-		return NULL;
-	}
-
-	memset(array, 0, sizeof(knot_dname_t *) * (max_id + 1));
-
-	for (uint i = 0; i < max_id - 1; i++) {
-		knot_dname_t *read_dname = read_dname_with_id(f, 1);
-		if (read_dname == NULL) {
-			dbg_zload("zload: create_dname_array: "
-			          "Cannot read dname.\n" );
-			cleanup_id_array(array, 0, i);
-			return NULL;
-		}
-
-		if (read_dname->id < max_id) {
-			/* Create new node from dname. */
-			read_dname->node = knot_node_new(read_dname, NULL, 0);
-			if (read_dname->node == NULL) {
-				dbg_zload("zload: create_dname_array: "
-				          "Cannot create new node "
-				          "from dname.\n");
-				/* Release read dname. */
-				knot_dname_release(read_dname);
-				cleanup_id_array(array, 0, i);
-				return NULL;
-			}
-
-			/* Store reference to dname in array. */
-			array[read_dname->id] = read_dname;
-		} else {
-			/* Release read dname. */
-			dbg_zload("zload: create_dname_array: "
-			          "dname id is out of range.\n");
-			knot_dname_release(read_dname);
-			cleanup_id_array(array, 0, i);
-			return NULL;
-		}
-
-	}
-	
-	dbg_zload("zload: create_dname_array: Array created.\n");
-	return array;
-}
-
 knot_zone_t *knot_zload_load(zloader_t *loader)
 {
 	dbg_zload("zload: load: Loading zone, loader: %p.\n", loader);
@@ -1209,243 +674,37 @@ knot_zone_t *knot_zload_load(zloader_t *loader)
 		dbg_zload("zload: load: NULL loader!\n");
 		return NULL;
 	}
-
-	FILE *f = loader->fp;
-
-	knot_node_t *tmp_node;
-
-	uint32_t node_count;
-	uint32_t nsec3_node_count;
-	uint32_t auth_node_count;
 	
-	int (*fread_wrapper)(void *dst, size_t size, size_t n, void *source);
-	fread_wrapper = fread_safe_from_file;
+	parser_context_t *c = loader->context;
 	
-	if (!fread_wrapper(&node_count, sizeof(node_count), 1, f)) {
-		dbg_zload("zload: load: Cannot read node count!\n");
-		return NULL;
-	}
-
-	if (!fread_wrapper(&nsec3_node_count, sizeof(nsec3_node_count), 1, f)) {
-		dbg_zload("zload: load: Cannot read NSEC3 node count!\n");
-		return NULL;
+	file_loader_process(loader->file_loader);
+	if (c->last_node && c->node_rrsigs) {
+		process_rrsigs_in_node(c, c->current_zone, c->last_node);
 	}
-	if (!fread_wrapper(&auth_node_count,
-	      sizeof(auth_node_count), 1, f)) {
-		dbg_zload("zload: load: Cannot read authoritative "
-		          "node count!\n");
+	if (c->ret != KNOT_EOK) {
+		log_zone_error("Zone could not be loaded (%d).", c->ret);
+		/*!< \todo Depending on the error, free stuff. */
+		rrset_list_delete(&c->node_rrsigs);
 		return NULL;
 	}
+	knot_zone_contents_adjust(c->current_zone);
+	rrset_list_delete(&c->node_rrsigs);
 	
-	dbg_zload_verb("zload: load: Authoritative nodes: %u.\n",
-	               auth_node_count);
-	dbg_zload_verb("zload: load: :oading %u nodes.\n", node_count);
-
-	uint32_t total_dnames = 0;
-	/* First, read number of dnames in dname table. */
-	if (!fread_wrapper(&total_dnames, sizeof(total_dnames), 1, f)) {
-		return NULL;
-	}
-
-	dbg_zload_verb("zload: load: Total dname count: %d.\n", total_dnames);
-
-	/* Create id array. */
-	knot_dname_t **id_array = create_dname_array(f, total_dnames);
-	if (id_array == NULL) {
-		dbg_zload("zload: load: Cannot create ID array.\n");
-		return NULL;
-	}
-
-	knot_dname_table_t *dname_table =
-		create_dname_table_from_array(id_array, total_dnames);
-	if (dname_table == NULL) {
-		dbg_zload("zload: load: Cannot create ID array.\n");
-		cleanup_id_array(id_array, 1, total_dnames);
-		free(dname_table);
-		return NULL;
-	}
-
-	knot_node_t *apex = knot_load_node(f, id_array);
-
-	if (!apex) {
-		dbg_zload("zone: Could not load apex node (in %s)\n",
-			loader->filename);
-		cleanup_id_array(id_array, 1,
-				 node_count + nsec3_node_count + 1);
-		free(dname_table);
-		return NULL;
-	}
-
-	dbg_zload_verb("zload: load: Apex node loaded: %p.\n", apex);
-
-	knot_zone_t *zone = knot_zone_new(apex, auth_node_count, 0);
-	if (zone == NULL) {
-		cleanup_id_array(id_array, 1,
-				 node_count + nsec3_node_count + 1);
-		dbg_zload("zload: load: Failed to create new "
-		          "zone from apex!\n");
-		knot_node_free(&apex);
-		free(dname_table);
-		return NULL;
-	}
-
-	knot_zone_contents_t *contents = knot_zone_get_contents(zone);
-	assert(contents);
-
-	/* Assign dname table to the new zone. */
-	contents->dname_table = dname_table;
-
-	knot_node_set_previous(apex, NULL);
-	knot_node_t *last_node = 0;
-	last_node = apex;
-
-	int ret = 0;
-
-	for (uint i = 1; i < node_count; i++) {
-		tmp_node = knot_load_node(f, id_array);
-		if (tmp_node != NULL) {
-			dbg_zload_detail("zload: load: Adding node owned by: "
-			                 "%s\n.",
-			                 knot_dname_to_str(tmp_node->owner));
-			if ((ret = knot_zone_contents_add_node(contents,
-			                                       tmp_node,
-			                                       0, 0, 0)) != 0) {
-				cleanup_id_array(id_array, 1,
-				                 node_count +
-				                 nsec3_node_count + 1);
-				knot_zone_deep_free(&zone, 0);
-				dbg_zload("zload: load: Failed to add node "
-				          "to zone: %s.\n", knot_strerror(ret));
-				return NULL;
-			}
-			
-			if (knot_dname_is_wildcard(tmp_node->owner)) {
-				find_and_set_wildcard_child(contents,
-				                            tmp_node, 0);
-			}
-
-			knot_node_set_previous(tmp_node, last_node);
-
-			if (tmp_node->rrset_count &&
-			    (knot_node_is_deleg_point(tmp_node) ||
-			    !knot_node_is_non_auth(tmp_node))) {
-				last_node = tmp_node;
-			}
-
-		} else {
-			dbg_zload("zload: load: Node error (in %s).\n",
-				loader->filename);
-			knot_zone_deep_free(&zone, 0);
-			cleanup_id_array(id_array, node_count + 1,
-					 nsec3_node_count + 1);
-			return NULL;
-		}
-	}
-
-	assert(knot_node_previous(knot_zone_contents_apex(contents)) == NULL);
-
-	knot_node_set_previous(knot_zone_contents_get_apex(contents),
-	                         last_node);
-
-	dbg_zload_detail("zload: load: Loading %u nsec3 nodes\n",
-	                 nsec3_node_count);
-
-	knot_node_t *nsec3_first = NULL;
-
-	if (nsec3_node_count > 0) {
-		nsec3_first = knot_load_node(f, id_array);
-		if (nsec3_first == NULL) {
-			log_zone_error("Cannot load NSEC3 data, "
-			               "zone database is probably corrupt.\n");
-		}
-
-		if ((ret = knot_zone_contents_add_nsec3_node(contents,
-		                                             nsec3_first,
-		                                             0, 0, 0)) != 0) {
-			dbg_zload("zload: load: "
-			          "cannot add first nsec3 node, "
-			          "exiting: %s.\n", knot_strerror(ret));
-			knot_zone_deep_free(&zone, 0);
-			cleanup_id_array(id_array, node_count + 1,
-					 nsec3_node_count + 1);
-			log_zone_error("Cannot store NSEC3 data, "
-			               "zone database is probably corrupt.\n");
-			return NULL;
-		}
-
-		knot_node_set_previous(nsec3_first, NULL);
-		last_node = nsec3_first;
-	}
-
-	for (uint i = 1; i < nsec3_node_count; i++) {
-		tmp_node = knot_load_node(f, id_array);
-
-		if (tmp_node != NULL) {
-			if ((ret = knot_zone_contents_add_nsec3_node(contents,
-			                 tmp_node, 0, 0, 0)) != 0) {
-				dbg_zload("zload: load: Cannot add "
-				          "NSEC3 node: %s.\n",
-				          knot_strerror(ret));
-				knot_zone_deep_free(&zone, 0);
-				cleanup_id_array(id_array, node_count + 1,
-						 nsec3_node_count + 1);
-				return NULL;
-			}
-
-			knot_node_set_previous(tmp_node, last_node);
-
-			last_node = tmp_node;
-		} else {
-			log_zone_error("Cannot load NSEC3 node. "
-			               "Zone database is probably "
-			               "currupted.\n");
-			knot_zone_deep_free(&zone, 0);
-			cleanup_id_array(id_array, node_count + 1,
-					 nsec3_node_count + 1);
-			return NULL;
-		}
-	}
-
-	if (nsec3_node_count) {
-		assert(knot_node_previous(nsec3_first) == NULL);
-		knot_node_set_previous(nsec3_first, last_node);
-	}
-
-	/* ID array is now useless */
-	for (uint i = 1; i < total_dnames; i++) {
-		/* Added to table, may discard now. */
-		knot_dname_release(id_array[i]);
-	}
-	free(id_array);
-
-	dbg_zload("zload: load: Zone loaded, returning: %p,\n", zone);
-	return zone;
+	return c->current_zone->zone;
 }
 
 int knot_zload_needs_update(zloader_t *loader)
 {
+	assert(0);
 	if (!loader) {
 		return 1;
 	}
 	
-        /* Check if the source still exists. */
-        struct stat st_src;
-        if (stat(loader->source, &st_src) != 0) {
-                return 1;
-        }
-
-        /* Check if the compiled file still exists. */
-        struct stat st_bin;
-        if (stat(loader->filename, &st_bin) != 0) {
-                return 1;
-        }
-	
-
 	/* Compare the mtime of the source and file. */
 	/*! \todo Inspect types on Linux. */
-	if (timet_cmp(st_bin.st_mtime, st_src.st_mtime) < 0) {
-		return 1;
-	}
+//	if (timet_cmp(st_bin.st_mtime, st_src.st_mtime) < 0) {
+//		return 1;
+//	}
 
 	return 0;
 }
@@ -1455,37 +714,10 @@ void knot_zload_close(zloader_t *loader)
 	if (!loader) {
 		return;
 	}
+	
+	file_loader_free(loader->file_loader);
 
-	free(loader->filename);
 	free(loader->source);
-	fclose(loader->fp);
+	free(loader->origin);
 	free(loader);
 }
-
-int knot_zload_rrset_deserialize(knot_rrset_t **rrset,
-                                   uint8_t *stream, size_t *size)
-{
-	if (stream == NULL || size == 0) {
-		dbg_zload("zload: rrset_deserialize: Bad arguments.\n");
-		return KNOT_EINVAL;
-	}
-
-	load_stream_t data;
-	data.stream = stream;
-	data.stream_remaining = *size;
-	data.stream_size = *size;
-
-	knot_rrset_t *ret = knot_load_rrset(&data, NULL, 0);
-	if (ret == NULL) {
-		dbg_zload("zload: rrset_deserialize: Cannot load RRSet.\n");
-		return KNOT_EMALF;
-	}
-
-	*size = data.stream_remaining;
-	*rrset = ret;
-
-	dbg_zload_detail("zload: rrset_deserialize: RRSet deserialized "
-	                 "successfully.\n");
-	return KNOT_EOK;
-}
-
diff --git a/src/knot/zone/zone-load.h b/src/knot/zone/zone-load.h
index 837d5f267d9366a16be5dad2c6b6a144bc844aaf..763f406abd0e7ed01bc46f8b62ecf84e67673c87 100644
--- a/src/knot/zone/zone-load.h
+++ b/src/knot/zone/zone-load.h
@@ -16,11 +16,11 @@
 /*!
  * \file zone-load.h
  *
+ * \author Marek Vavrusa <marek.vavrusa@nic.cz>
  * \author Jan Kadlec <jan.kadlec@nic.cz>
  *
- * \brief Loader of previously parsed zone
+ * \brief Zone loading
  *
- * \addtogroup zone-load-dump
  * @{
  */
 
@@ -30,15 +30,44 @@
 #include <stdio.h>
 
 #include "libknot/zone/zone.h"
+#include "zscanner/file_loader.h"
+
+#define MAGIC_LENGTH 8
+#define MAGIC "knotv130"
+
+/* TODO this structure is highly redundant, remove. Maybe use oh-so-great BIRD lists. */
+/*!
+ * \brief One-purpose linked list holding pointers to RRSets.
+ */
+struct rrset_list {
+	knot_rrset_t *data; /*!< List data. */
+	struct rrset_list *next; /*!< Next node. */
+};
+
+typedef struct rrset_list rrset_list_t;
+
+
+struct parser_context {
+	rrset_list_t *node_rrsigs;
+	knot_zone_contents_t *current_zone;
+	knot_rrset_t *current_rrset;
+	knot_dname_t *origin_from_config;
+	knot_node_t *last_node;
+	int ret;
+};
+
+typedef struct parser_context parser_context_t;
 
 /*!
  * \brief Zone loader structure.
  */
 typedef struct zloader_t
 {
-	char *filename;           /*!< Compiled zone filename. */
 	char *source;             /*!< Zone source file. */
-	FILE *fp;                 /*!< Open filepointer to compiled zone. */
+	char *origin;             /*!< Zone's origin string. */
+	int semantic_checks;      /*!< Wanted level of semantic checks. */
+	file_loader_t *file_loader;/*!< Scanner's file loader. */
+	parser_context_t *context;/*!< Loader context. */
 
 } zloader_t;
 
@@ -51,7 +80,8 @@ typedef struct zloader_t
  * \retval Initialized loader on success.
  * \retval NULL on error.
  */
-int knot_zload_open(zloader_t **loader, const char *filename);
+int knot_zload_open(zloader_t **loader, const char *source, const char *origin,
+                    int semantic_checks);
 
 /*!
  * \brief Loads zone from a compiled and serialized zone file.
@@ -71,9 +101,9 @@ knot_zone_t *knot_zload_load(zloader_t *loader);
  * \retval 1 is if needs to be recompiled.
  * \retval 0 if it is up to date.
  */
+//TODO will not work, has to look at serials probably
 int knot_zload_needs_update(zloader_t *loader);
 
-
 /*!
  * \brief Free zone loader.
  *
@@ -81,24 +111,6 @@ int knot_zload_needs_update(zloader_t *loader);
  */
 void knot_zload_close(zloader_t *loader);
 
-/*!
- * \brief Loads RRSet serialized by knot_zdump_rrset_serialize().
- *
- * \param stream Stream containing serialized RRSet.
- * \param size Size of stream. This variable will contain remaining length of
- *        stream, once the function has ended.
- * \param rrset Place for created RRSet.
- *
- * \note If RRSet contains RRSIGs, their owners are not copies, but only links
- *       to the owner of RRSet. All RDATA dnames are copied.
- *
- * \retval KNOT_EOK on success.
- * \retval KNOT_EBADAG on wrong arguments.
- * \retval KNOT_EMALF when stream is malformed.
- */
-int knot_zload_rrset_deserialize(knot_rrset_t **rrset,
-                                   uint8_t *stream, size_t *size);
-
 #endif /* _KNOTD_ZONELOAD_H_ */
 
 /*! @} */
diff --git a/src/libknot/nameserver/name-server.c b/src/libknot/nameserver/name-server.c
index 27ad3255d9055fd5991b2fc2ae8e36a2ee02a044..86c289a00a2f3b942a91010c57a4eaf542ccdd7e 100644
--- a/src/libknot/nameserver/name-server.c
+++ b/src/libknot/nameserver/name-server.c
@@ -24,6 +24,8 @@
 #include "updates/xfr-in.h"
 
 #include "libknot.h"
+#include "common/errcode.h"
+#include "common.h"
 #include "util/debug.h"
 #include "packet/packet.h"
 #include "packet/response.h"
diff --git a/src/libknot/packet/packet.c b/src/libknot/packet/packet.c
index c1823a8c9e7b5c201ca6ea3908e9e8d59838ae79..04a48ec15808a213f0afe762548b05f9716540b4 100644
--- a/src/libknot/packet/packet.c
+++ b/src/libknot/packet/packet.c
@@ -15,6 +15,7 @@
  */
 
 #include <assert.h>
+#include <stdlib.h>
 
 #include "packet/packet.h"
 #include "util/debug.h"
diff --git a/src/libknot/updates/ddns.c b/src/libknot/updates/ddns.c
index 5f0473db90e5b185d57af9b13b000984de7ec9ed..5441e122148b9e65952386ae74b7424f8446b2a7 100644
--- a/src/libknot/updates/ddns.c
+++ b/src/libknot/updates/ddns.c
@@ -15,11 +15,13 @@
  */
 
 #include <assert.h>
+#include <stdlib.h>
 
 #include "updates/ddns.h"
 #include "updates/changesets.h"
 #include "util/debug.h"
 #include "packet/packet.h"
+#include "common.h"
 #include "consts.h"
 #include "common/mempattern.h"
 #include "nameserver/name-server.h"  // ns_serial_compare() - TODO: extract
diff --git a/src/libknot/updates/xfr-in.c b/src/libknot/updates/xfr-in.c
index 18a3948773080d7e136c32ad856dab63cf2e97d0..d93e92a54f17e2f65bd19ecad5a969d70a726c1b 100644
--- a/src/libknot/updates/xfr-in.c
+++ b/src/libknot/updates/xfr-in.c
@@ -26,6 +26,7 @@
 #include "dname.h"
 #include "zone/zone.h"
 #include "packet/query.h"
+#include "common.h"
 #include "updates/changesets.h"
 #include "tsig.h"
 #include "tsig-op.h"
@@ -1244,8 +1245,6 @@ static void xfrin_zone_contents_free(knot_zone_contents_t **contents)
 	knot_zone_tree_deep_free(&(*contents)->nsec3_nodes);
 
 	knot_nsec3_params_free(&(*contents)->nsec3_params);
-
-	knot_dname_table_deep_free(&(*contents)->dname_table);
 	
 	free(*contents);
 	*contents = NULL;
@@ -2418,27 +2417,6 @@ static void xfrin_switch_nodes_in_node(knot_node_t *node, void *data)
 
 /*----------------------------------------------------------------------------*/
 
-static void xfrin_switch_node_in_hash_table(ck_hash_table_item_t *item,
-                                            void *data)
-{
-	UNUSED(data);
-
-	if (item == NULL) {
-		return;
-	}
-
-	knot_node_t *node = (knot_node_t *)item->value;
-	knot_node_t *new_node = knot_node_get_new_node(node);
-
-	assert(new_node != NULL);
-
-	if (new_node != NULL) {
-		item->value = new_node;
-	}
-}
-
-/*----------------------------------------------------------------------------*/
-
 static void xfrin_switch_node_in_dname_table(knot_dname_t *dname, void *data)
 {
 	UNUSED(data);
@@ -2505,8 +2483,6 @@ static void xfrin_zone_contents_free2(knot_zone_contents_t **contents)
 
 	knot_nsec3_params_free(&(*contents)->nsec3_params);
 
-	knot_dname_table_deep_free(&(*contents)->dname_table);
-
 	free(*contents);
 	*contents = NULL;
 }
@@ -3010,12 +2986,10 @@ static int xfrin_remove_empty_nodes(knot_zone_contents_t *contents,
 	dbg_xfrin_verb("OLD NSEC3 NODES COUNT: %d\n", changes->old_nsec3_count);
 
 	// remove these nodes from both hash table and the tree
-	ck_hash_table_item_t *hash_item = NULL;
 	knot_zone_tree_node_t *zone_node = NULL;
 
 	for (int i = 0; i < changes->old_nodes_count; ++i) {
 		zone_node = NULL;
-		hash_item = NULL;
 
 dbg_xfrin_exec_detail(
 		char *name = knot_dname_to_str(knot_node_owner(
@@ -3026,15 +3000,12 @@ dbg_xfrin_exec_detail(
 );
 
 		ret = knot_zone_contents_remove_node(
-			contents, changes->old_nodes[i], &zone_node,
-			&hash_item);
+			contents, changes->old_nodes[i], &zone_node);
 
 		if (ret != KNOT_EOK) {
 			dbg_xfrin("Failed to remove node from zone!\n");
 			return KNOT_ENONODE;
 		}
-
-		free(hash_item);
 		free(zone_node);
 	}
 
diff --git a/src/libknot/zone/zone-contents.c b/src/libknot/zone/zone-contents.c
index 55aa19cd7b559344307e3ecf729be2f342d5d0a3..3a325aa6199767c643b8c89d1a9579afa6561d84 100644
--- a/src/libknot/zone/zone-contents.c
+++ b/src/libknot/zone/zone-contents.c
@@ -948,17 +948,6 @@ knot_zone_contents_t *knot_zone_contents_new(knot_node_t *apex,
 		goto cleanup;
 	}
 
-	if (use_domain_table) {
-		dbg_zone_verb("Creating domain name table.\n");
-		contents->dname_table = knot_dname_table_new();
-		if (contents->dname_table == NULL) {
-			ERR_ALLOC_FAILED;
-			goto cleanup;
-		}
-	} else {
-		contents->dname_table = NULL;
-	}
-
 	//contents->node_count = node_count;
 
 	/* Initialize NSEC3 params */
@@ -996,7 +985,6 @@ knot_zone_contents_t *knot_zone_contents_new(knot_node_t *apex,
 
 cleanup:
 	dbg_zone_verb("Cleaning up.\n");
-	free(contents->dname_table);
 	free(contents->nodes);
 	free(contents->nsec3_nodes);
 	free(contents);
@@ -1490,8 +1478,7 @@ int knot_zone_contents_add_nsec3_rrset(knot_zone_contents_t *zone,
 /*----------------------------------------------------------------------------*/
 
 int knot_zone_contents_remove_node(knot_zone_contents_t *contents, 
-	const knot_node_t *node, knot_zone_tree_node_t **removed_tree, 
-	ck_hash_table_item_t **removed_hash)
+	const knot_node_t *node, knot_zone_tree_node_t **removed_tree)
 {
 	if (contents == NULL || node == NULL) {
 		return KNOT_EINVAL;
@@ -2210,14 +2197,6 @@ knot_zone_tree_t *knot_zone_contents_get_nsec3_nodes(
 
 /*----------------------------------------------------------------------------*/
 
-ck_hash_table_t *knot_zone_contents_get_hash_table(
-		knot_zone_contents_t *contents)
-{
-	return contents->table;
-}
-
-/*----------------------------------------------------------------------------*/
-
 /*----------------------------------------------------------------------------*/
 
 int knot_zone_contents_shallow_copy(const knot_zone_contents_t *from,
@@ -2271,7 +2250,6 @@ int knot_zone_contents_shallow_copy(const knot_zone_contents_t *from,
 cleanup:
 	knot_zone_tree_free(&contents->nodes);
 	knot_zone_tree_free(&contents->nsec3_nodes);
-	free(contents->dname_table);
 	free(contents);
 	return ret;
 }
@@ -2329,7 +2307,6 @@ int knot_zone_contents_shallow_copy2(const knot_zone_contents_t *from,
 cleanup:
 	knot_zone_tree_free(&contents->nodes);
 	knot_zone_tree_free(&contents->nsec3_nodes);
-	free(contents->dname_table);
 	free(contents);
 	return ret;
 }
@@ -2348,8 +2325,6 @@ void knot_zone_contents_free(knot_zone_contents_t **contents)
 
 	knot_nsec3_params_free(&(*contents)->nsec3_params);
 	
-	knot_dname_table_free(&(*contents)->dname_table);
-
 	free(*contents);
 	*contents = NULL;
 }
diff --git a/src/libknot/zone/zone-contents.h b/src/libknot/zone/zone-contents.h
index 67107566a8e18d21a18d98279feb027125184783..28e8ca7b21208d82a3f135d31f47ab0d20ed6c68 100644
--- a/src/libknot/zone/zone-contents.h
+++ b/src/libknot/zone/zone-contents.h
@@ -32,9 +32,7 @@
 #include "zone/node.h"
 #include "dname.h"
 #include "nsec3.h"
-#include "zone/dname-table.h"
 #include "common/tree.h"
-#include "hash/cuckoo-hash-table.h"
 
 #include "zone-tree.h"
 
@@ -45,12 +43,9 @@ struct knot_zone;
 typedef struct knot_zone_contents_t {
 	knot_node_t *apex;       /*!< Apex node of the zone (holding SOA) */
 
-	ck_hash_table_t *table;     /*!< Hash table for holding zone nodes. */
 	knot_zone_tree_t *nodes;
 	knot_zone_tree_t *nsec3_nodes;
 
-	knot_dname_table_t *dname_table;
-
 	struct knot_zone *zone;
 
 	knot_nsec3_params_t nsec3_params;
@@ -58,7 +53,7 @@ typedef struct knot_zone_contents_t {
 	/*!
 	 * \todo Unify the use of this field - authoritative nodes vs. all.
 	 */
-	uint node_count;
+	size_t node_count;
 
 	/*! \brief Various flags
 	 * 
@@ -80,7 +75,7 @@ typedef struct knot_zone_contents_t {
 /*----------------------------------------------------------------------------*/
 
 knot_zone_contents_t *knot_zone_contents_new(knot_node_t *apex,
-                                             uint node_count,
+                                             size_t node_count,
                                              int use_domain_table,
                                              struct knot_zone *zone);
 
@@ -181,8 +176,7 @@ int knot_zone_contents_add_nsec3_rrset(knot_zone_contents_t *contents,
                                          int use_domain_table);
 
 int knot_zone_contents_remove_node(knot_zone_contents_t *contents, 
-	const knot_node_t *node, knot_zone_tree_node_t **removed_tree, 
-	ck_hash_table_item_t **removed_hash);
+	const knot_node_t *node, knot_zone_tree_node_t **removed_tree);
 
 int knot_zone_contents_remove_nsec3_node(knot_zone_contents_t *contents, 
 	const knot_node_t *node, knot_zone_tree_node_t **removed);
@@ -506,9 +500,6 @@ knot_zone_tree_t *knot_zone_contents_get_nodes(
 knot_zone_tree_t *knot_zone_contents_get_nsec3_nodes(
 		knot_zone_contents_t *contents);
 
-ck_hash_table_t *knot_zone_contents_get_hash_table(
-		knot_zone_contents_t *contents);
-
 int knot_zone_contents_dname_table_apply(knot_zone_contents_t *contents,
                                            void (*function)(knot_dname_t *,
                                                             void *),
diff --git a/src/libknot/zone/zone-diff.c b/src/libknot/zone/zone-diff.c
index 16a9c108db6bc39f90fab2033ab8fea3f72d85dc..0da8277c756383c5203116cbb2a7dd3af038a898 100644
--- a/src/libknot/zone/zone-diff.c
+++ b/src/libknot/zone/zone-diff.c
@@ -16,8 +16,10 @@
 
 #include <assert.h>
 #include <config.h>
+#include <stdlib.h>
 
 #include "libknot/util/debug.h"
+#include "common/errcode.h"
 #include "zone-diff.h"
 #include "libknot/nameserver/name-server.h"
 #include "common/descriptor_new.h"
diff --git a/src/libknot/zone/zone.c b/src/libknot/zone/zone.c
index 40ac3ceed02c55881d29b3c6d991af54d7b04382..5783c5b025ced25eee8d93bfe530a77cc0cb356f 100644
--- a/src/libknot/zone/zone.c
+++ b/src/libknot/zone/zone.c
@@ -27,7 +27,6 @@
 #include "dname.h"
 #include "util/debug.h"
 #include "util/utils.h"
-#include "hash/cuckoo-hash-table.h"
 #include "zone/zone-contents.h"
 
 /*! \brief Adaptor for knot_zone_deep_free() */
diff --git a/src/libknot/zone/zone.h b/src/libknot/zone/zone.h
index 31ff2ac40a2ae4a378338a5fcb99fd94857f6106..1fd564cd7b80711934164f396474460355aa6d18 100644
--- a/src/libknot/zone/zone.h
+++ b/src/libknot/zone/zone.h
@@ -32,10 +32,8 @@
 #include "zone/node.h"
 #include "dname.h"
 #include "nsec3.h"
-#include "zone/dname-table.h"
 #include "common/tree.h"
 #include "common/ref.h"
-#include "hash/cuckoo-hash-table.h"
 
 #include "zone-tree.h"
 
@@ -109,7 +107,7 @@ knot_zone_t *knot_zone_new_empty(knot_dname_t *name);
  *
  * \return The initialized zone structure or NULL if an error occured.
  */
-knot_zone_t *knot_zone_new(knot_node_t *apex, uint node_count,
+knot_zone_t *knot_zone_new(knot_node_t *apex, size_t node_count,
                                int use_domain_table);
 
 knot_zone_contents_t *knot_zone_get_contents(
diff --git a/src/zcompile/parser-descriptor.c b/src/zcompile/parser-descriptor.c
deleted file mode 100644
index 26e1eb0bfe6b5aadbe23c0e3491eba38e3adbb45..0000000000000000000000000000000000000000
--- a/src/zcompile/parser-descriptor.c
+++ /dev/null
@@ -1,539 +0,0 @@
-/*!
- * \file parser-descriptor.c
- *
- * \author Modifications by Jan Kadlec <jan.kadlec@nic.cz>,
- *         most of the work by NLnet Labs.
- *         Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * \brief Contains resource record descriptor and its API
- *
- * \addtogroup zoneparser
- * @{
- */
-
-/*
- * Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * This software is open source.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- *
- * Neither the name of the NLNET LABS nor the names of its contributors may
- * be used to endorse or promote products derived from this software without
- * specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include <config.h>
-#include <stdlib.h>
-#include <string.h>
-#include <stdio.h>
-#include <ctype.h>
-#include <assert.h>
-#include <string.h>
-#include <sys/types.h>
-
-//#include "common.h"
-#include "zcompile/parser-descriptor.h"
-/* TODO this has to be removed - move tokens to separate file
-	but can it be done?) */
-#include "zcompile/zcompile.h"
-/* FIXME: Generate .y and .l to zoneparser/ */
-#include "zparser.h"
-
-enum desclen { PARSER_RRTYPE_DESCRIPTORS_LENGTH = 65536 }; // used to be 101
-
-/* Taken from RFC 1035, section 3.2.4.  */
-static knot_lookup_table_t dns_rrclasses[] = {
-	{ PARSER_CLASS_IN, "IN" },	/* the Internet */
-	{ PARSER_CLASS_CS, "CS" },	/* the CSNET class (Obsolete) */
-	{ PARSER_CLASS_CH, "CH" },	/* the CHAOS class */
-	{ PARSER_CLASS_HS, "HS" },	/* Hesiod */
-	{ 0, NULL }
-};
-static parser_rrtype_descriptor_t
-       knot_rrtype_descriptors[PARSER_RRTYPE_DESCRIPTORS_LENGTH] = {
-	/* 0 */
-	{ 0, 0, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 1 */
-	{ PARSER_RRTYPE_A, T_A, "A", 1, { PARSER_RDATA_WF_A }, true },
-	/* 2 */
-	{ PARSER_RRTYPE_NS, T_NS, "NS", 1,
-	{ PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 3 */
-	{ PARSER_RRTYPE_MD, T_MD, "MD", 1,
-	  { PARSER_RDATA_WF_UNCOMPRESSED_DNAME }, true },
-	/* 4 */
-	{ PARSER_RRTYPE_MF, T_MF, "MF", 1,
-	  { PARSER_RDATA_WF_UNCOMPRESSED_DNAME }, true },
-	/* 5 */
-	{ PARSER_RRTYPE_CNAME, T_CNAME, "CNAME", 1,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 6 */
-	{ PARSER_RRTYPE_SOA, T_SOA, "SOA", 7,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME, PARSER_RDATA_WF_COMPRESSED_DNAME,
-	    PARSER_RDATA_WF_LONG, PARSER_RDATA_WF_LONG, PARSER_RDATA_WF_LONG,
-	    PARSER_RDATA_WF_LONG, PARSER_RDATA_WF_LONG }, true },
-	/* 7 */
-	{ PARSER_RRTYPE_MB, T_MB, "MB", 1,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 8 */
-	{ PARSER_RRTYPE_MG, T_MG, "MG", 1,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 9 */
-	{ PARSER_RRTYPE_MR, T_MR, "MR", 1,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 10 */
-	{ PARSER_RRTYPE_NULL, T_NULL, NULL, 1,
-	  { PARSER_RDATA_WF_BINARY }, true },
-	/* 11 */
-	{ PARSER_RRTYPE_WKS, T_WKS, "WKS", 2,
-	  { PARSER_RDATA_WF_A, PARSER_RDATA_WF_BINARY }, true },
-	/* 12 */
-	{ PARSER_RRTYPE_PTR, T_PTR, "PTR", 1,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 13 */
-	{ PARSER_RRTYPE_HINFO, T_HINFO, "HINFO", 2,
-	  { PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT }, true },
-	/* 14 */
-	{ PARSER_RRTYPE_MINFO, T_MINFO, "MINFO", 2,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME,
-	    PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 15 */
-	{ PARSER_RRTYPE_MX, T_MX, "MX", 2,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 16 */ /* This is obscure, but I guess there's no other way */
-	{ PARSER_RRTYPE_TXT, T_TXT, "TXT", PARSER_MAX_RDATA_ITEMS,
-	  { PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT }, false },
-	/* 17 */
-	{ PARSER_RRTYPE_RP, T_RP, "RP", 2,
-	  { PARSER_RDATA_WF_COMPRESSED_DNAME,
-	    PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 18 */
-	{ PARSER_RRTYPE_AFSDB, T_AFSDB, "AFSDB", 2,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 19 */
-	{ PARSER_RRTYPE_X25, T_X25, "X25", 1,
-	  { PARSER_RDATA_WF_TEXT }, true },
-	/* 20 */
-	{ PARSER_RRTYPE_ISDN, T_ISDN, "ISDN", 2,
-	  { PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT }, false },
-	/* 21 */
-	{ PARSER_RRTYPE_RT, T_RT, "RT", 2,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_COMPRESSED_DNAME }, true },
-	/* 22 */
-	{ PARSER_RRTYPE_NSAP, T_NSAP, "NSAP", 1,
-	  { PARSER_RDATA_WF_BINARY }, true },
-	/* 23 */
-	{ 23, 0, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 24 */
-	{ PARSER_RRTYPE_SIG, T_SIG, "SIG", 9,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BYTE,
-	    PARSER_RDATA_WF_LONG, PARSER_RDATA_WF_LONG, PARSER_RDATA_WF_LONG,
-	    PARSER_RDATA_WF_SHORT,PARSER_RDATA_WF_UNCOMPRESSED_DNAME,
-	    PARSER_RDATA_WF_BINARY }, true },
-	/* 25 */
-	{ PARSER_RRTYPE_KEY, T_KEY, "KEY", 4,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_BYTE,
-	    PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BINARY }, true },
-	/* 26 */
-	{ PARSER_RRTYPE_PX, T_PX, "PX", 3,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_UNCOMPRESSED_DNAME,
-	    PARSER_RDATA_WF_UNCOMPRESSED_DNAME }, true },
-	/* 27 */
-	{ 27, 0, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 28 */
-	{ PARSER_RRTYPE_AAAA, T_AAAA, "AAAA", 1,
-	  { PARSER_RDATA_WF_AAAA }, true },
-	/* 29 */
-	{ PARSER_RRTYPE_LOC, T_LOC, "LOC", 1,
-	  { PARSER_RDATA_WF_BINARY }, true },
-	/* 30 */
-	{ PARSER_RRTYPE_NXT, T_NXT, "NXT", 2,
-	  { PARSER_RDATA_WF_UNCOMPRESSED_DNAME,
-	    PARSER_RDATA_WF_BINARY }, true },
-	/* 31 */
-	{ 31, 0, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 32 */
-	{ 32, 0, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 33 */
-	{ PARSER_RRTYPE_SRV, T_SRV, "SRV", 4,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_SHORT,
-	    PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_UNCOMPRESSED_DNAME },
-	  true },
-	/* 34 */
-	{ 34, 0, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 35 */
-	{ PARSER_RRTYPE_NAPTR, T_NAPTR, "NAPTR", 6,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_UNCOMPRESSED_DNAME }, true },
-	/* 36 */
-	{ PARSER_RRTYPE_KX, T_KX, "KX", 2,
-	  { PARSER_RDATA_WF_SHORT,
-	    PARSER_RDATA_WF_UNCOMPRESSED_DNAME }, true },
-	/* 37 */
-	{ PARSER_RRTYPE_CERT, T_CERT, "CERT", 4,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_SHORT,
-	    PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BINARY }, true },
-	/* 38 */
-	{ PARSER_RRTYPE_A6, T_A6, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 39 */
-	{ PARSER_RRTYPE_DNAME, T_DNAME, "DNAME", 1,
-	  { PARSER_RDATA_WF_UNCOMPRESSED_DNAME }, true },
-	/* 40 */
-	{ 40, 0, NULL, 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 41 */
-	/* OPT has its parser token, but should never be in zone file... */
-	{ PARSER_RRTYPE_OPT, T_OPT, "OPT", 1,
-	  { PARSER_RDATA_WF_BINARY }, true },
-	/* 42 */
-	{ PARSER_RRTYPE_APL, T_APL, "APL", PARSER_MAX_RDATA_ITEMS,
-	  { PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL,
-	    PARSER_RDATA_WF_APL, PARSER_RDATA_WF_APL }, false },
-	/* 43 */
-	{ PARSER_RRTYPE_DS, T_DS, "DS", 4,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_BYTE,
-	  PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BINARY }, true },
-	/* 44 */
-	{ PARSER_RRTYPE_SSHFP, T_SSHFP, "SSHFP", 3,
-	  { PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BYTE,
-	    PARSER_RDATA_WF_BINARY }, true },
-	/* 45 */
-	{ PARSER_RRTYPE_IPSECKEY, T_IPSECKEY, "IPSECKEY", 5,
-	  { PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BYTE,
-	    PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_IPSECGATEWAY,
-	    PARSER_RDATA_WF_BINARY }, false },
-	/* 46 */
-	{ PARSER_RRTYPE_RRSIG, T_RRSIG, "RRSIG", 9,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_BYTE,
-	    PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_LONG,
-	    PARSER_RDATA_WF_LONG, PARSER_RDATA_WF_LONG,
-	    PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_BINARY,
-	    PARSER_RDATA_WF_BINARY }, true },
-	/* 47 */
-	{ PARSER_RRTYPE_NSEC, T_NSEC, "NSEC", 2,
-	  { PARSER_RDATA_WF_BINARY, PARSER_RDATA_WF_BINARY }, true },
-	/* 48 */
-	{ PARSER_RRTYPE_DNSKEY, T_DNSKEY, "DNSKEY", 4,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_BYTE,
-	    PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BINARY }, true },
-	/* 49 */
-	{ PARSER_RRTYPE_DHCID, T_DHCID, "DHCID", 1, { PARSER_RDATA_WF_BINARY }, true },
-	/* 50 */
-	{ PARSER_RRTYPE_NSEC3, T_NSEC3, "NSEC3", 6,
-	  { PARSER_RDATA_WF_BYTE, /* hash type */
-	    PARSER_RDATA_WF_BYTE, /* flags */
-	    PARSER_RDATA_WF_SHORT, /* iterations */
-	    PARSER_RDATA_WF_BINARYWITHLENGTH, /* salt */
-	    PARSER_RDATA_WF_BINARYWITHLENGTH, /* next hashed name */
-	    PARSER_RDATA_WF_BINARY /* type bitmap */ }, true },
-	/* 51 */
-	{ PARSER_RRTYPE_NSEC3PARAM, T_NSEC3PARAM, "NSEC3PARAM", 4,
-	  { PARSER_RDATA_WF_BYTE, /* hash type */
-	    PARSER_RDATA_WF_BYTE, /* flags */
-	    PARSER_RDATA_WF_SHORT, /* iterations */
-	    PARSER_RDATA_WF_BINARYWITHLENGTH /* salt */ }, true },
-	/* 52 TLSA */
-        { PARSER_RRTYPE_TLSA, T_TLSA, "TLSA", 3,
-          { PARSER_RDATA_WF_BYTE,
-            PARSER_RDATA_WF_BYTE,
-            PARSER_RDATA_WF_BYTE,
-            PARSER_RDATA_WF_BINARY}, true }, 
-
-
-    /* In NSD they have indices between 52 and 99 filled with
-     unknown types. TODO add here if it's really needed? */
-     /* it is indeed needed, in rrtype_from_string */
-
-    /* There's a GNU extension that works like this: [first ... last] = value */
-
-        [53 ... 98] = { PARSER_RRTYPE_TYPEXXX, T_UTYPE, NULL, 1, { PARSER_RDATA_WF_BINARY }},
-
-	/* 99 */
-	[99] = { PARSER_RRTYPE_SPF, T_SPF, "SPF", PARSER_MAX_RDATA_ITEMS,
-	  { PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT,
-	    PARSER_RDATA_WF_TEXT, PARSER_RDATA_WF_TEXT }, false },
-	[100 ... 32768] = { PARSER_RRTYPE_TYPEXXX, T_UTYPE, NULL, 1, { PARSER_RDATA_WF_BINARY }},
-	/* 32769 */
-	[32769] = { PARSER_RRTYPE_DLV, T_DLV, "DLV", 4,
-	  { PARSER_RDATA_WF_SHORT, PARSER_RDATA_WF_BYTE,
-	    PARSER_RDATA_WF_BYTE, PARSER_RDATA_WF_BINARY }}, 
-	[32770 ... 65535] = { PARSER_RRTYPE_TYPEXXX, T_UTYPE, NULL, 1, { PARSER_RDATA_WF_BINARY }}
-};
-
-parser_rrtype_descriptor_t *parser_rrtype_descriptor_by_type(uint16_t type)
-{
-	return &knot_rrtype_descriptors[type];
-}
-
-/* I see a lot of potential here to speed up zone parsing - this is O(n) *
- * could be better */
-parser_rrtype_descriptor_t *parser_rrtype_descriptor_by_name(const char *name)
-{
-	if (!name) {
-		return NULL;
-	}
-
-	if (strcasecmp(name, "IN") == 0) {
-		return NULL;
-	}
-
-	if (isdigit((int)name[0])) {
-		return NULL;
-	}
-
-//	/* The most common - A and NS. */
-//	if (strcasecmp(name, "NS") == 0) {
-//		return &knot_rrtype_descriptors[2];
-//	}
-
-//	if (strcasecmp(name, "A") == 0) {
-//		return &knot_rrtype_descriptors[1];
-//	}
-
-//	/* Then RRSIG */
-//	if (strcasecmp(name, "RRSIG") == 0) {
-//		return &knot_rrtype_descriptors[46];
-//	}
-
-//	/* Then DS */
-//	if (strcasecmp(name, "DS") == 0) {
-//		return &knot_rrtype_descriptors[43];
-//	}
-//	/* Then NSEC3 */
-//	if (strcasecmp(name, "NSEC3") == 0) {
-//		return &knot_rrtype_descriptors[50];
-//	}
-//	/* Then NSEC */
-//	if (strcasecmp(name, "NSEC") == 0) {
-//		return &knot_rrtype_descriptors[47];
-//	}
-
-	int i;
-
-	for (i = 0; i < PARSER_RRTYPE_LAST + 1; ++i) {
-		if (knot_rrtype_descriptors[i].name &&
-		    strcasecmp(knot_rrtype_descriptors[i].name, name) == 0) {
-			return &knot_rrtype_descriptors[i];
-		}
-	}
-
-	if (knot_rrtype_descriptors[PARSER_RRTYPE_DLV].name &&
-	    strcasecmp(knot_rrtype_descriptors[PARSER_RRTYPE_DLV].name,
-				      name) == 0) {
-		return &knot_rrtype_descriptors[PARSER_RRTYPE_DLV];
-	}
-
-	return NULL;
-}
-
-const char *parser_rrtype_to_string(uint16_t rrtype)
-{
-	static char buf[20];
-	parser_rrtype_descriptor_t *descriptor =
-		parser_rrtype_descriptor_by_type(rrtype);
-	if (descriptor->name) {
-		return descriptor->name;
-	} else {
-		snprintf(buf, sizeof(buf), "TYPE%d", (int) rrtype);
-		return buf;
-	}
-}
-
-uint16_t parser_rrtype_from_string(const char *name)
-{
-	char *end;
-	long rrtype;
-	parser_rrtype_descriptor_t *entry;
-
-	entry = parser_rrtype_descriptor_by_name(name);
-	if (entry) {
-		return entry->type;
-	}
-
-	if (strlen(name) < 5) {
-		return 0;
-	}
-
-	if (strncasecmp(name, "TYPE", 4) != 0) {
-		return 0;
-	}
-
-	if (!isdigit((int)name[4])) {
-		return 0;
-	}
-
-	/* The rest from the string must be a number.  */
-	rrtype = strtol(name + 4, &end, 10);
-	if (*end != '\0') {
-		return 0;
-	}
-	if (rrtype < 0 || rrtype > 65535L) {
-		return 0;
-	}
-
-	return (uint16_t) rrtype;
-}
-
-const char *parser_rrclass_to_string(uint16_t rrclass)
-{
-	static char buf[20];
-	knot_lookup_table_t *entry = knot_lookup_by_id(dns_rrclasses,
-							   rrclass);
-	if (entry) {
-		assert(strlen(entry->name) < sizeof(buf));
-		knot_strlcpy(buf, entry->name, sizeof(buf));
-	} else {
-		snprintf(buf, sizeof(buf), "CLASS%d", (int) rrclass);
-	}
-	return buf;
-}
-
-uint16_t parser_rrclass_from_string(const char *name)
-{
-	char *end;
-	long rrclass;
-	knot_lookup_table_t *entry;
-
-	entry = knot_lookup_by_name(dns_rrclasses, name);
-	if (entry) {
-		return (uint16_t) entry->id;
-	}
-
-	if (strlen(name) < 6) {
-		return 0;
-	}
-
-	if (strncasecmp(name, "CLASS", 5) != 0) {
-		return 0;
-	}
-
-	if (!isdigit((int)name[5])) {
-		return 0;
-	}
-
-	// The rest from the string must be a number.
-	rrclass = strtol(name + 5, &end, 10);
-	if (*end != '\0') {
-		return 0;
-	}
-	if (rrclass < 0 || rrclass > 65535L) {
-		return 0;
-	}
-
-	return (uint16_t) rrclass;
-}
-
-/*! @} */
diff --git a/src/zcompile/parser-descriptor.h b/src/zcompile/parser-descriptor.h
deleted file mode 100644
index 48c6f021c623f48531ca2b89f94480f01d69ea19..0000000000000000000000000000000000000000
--- a/src/zcompile/parser-descriptor.h
+++ /dev/null
@@ -1,279 +0,0 @@
-/*!
- * \file parser-descriptor.h
- *
- * \author Modifications by Jan Kadlec <jan.kadlec@nic.cz>,
- *         most of the work by NLnet Labs.
- *         Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * \brief Contains resource record descriptor and its API
- * 
- * \addtogroup zoneparser
- * @{
- */
-
-/*
- * Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * This software is open source.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- *
- * Neither the name of the NLNET LABS nor the names of its contributors may
- * be used to endorse or promote products derived from this software without
- * specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef _KNOTD_PARSER_DESCRIPTOR_H_
-#define _KNOTD_PARSER_DESCRIPTOR_H_
-
-#include <stdint.h>
-#include <stdbool.h>
-
-#include "libknot/util/utils.h"
-
-enum parser_mxrdtln {
-	PARSER_MAX_RDATA_ITEMS = 64,
-	PARSER_MAX_RDATA_ITEM_SIZE = 255,
-	PARSER_MAX_RDATA_WIRE_SIZE =
-	PARSER_MAX_RDATA_ITEMS * PARSER_MAX_RDATA_ITEM_SIZE
-};
-//#define MAXRDATALEN 64
-
-/* 64 is in NSD. Seems a little too much, but I'd say it's not a real issue. */
-
-/*!
- * \brief Enum containing RR class codes.
- */
-enum parser_rr_class {
-	PARSER_CLASS_IN = 1,
-	PARSER_CLASS_CS,
-	PARSER_CLASS_CH,
-	PARSER_CLASS_HS,
-	PARSER_CLASS_NONE = 254,
-	PARSER_CLASS_ANY = 255
-};
-
-typedef enum parser_rr_class parser_rr_class_t;
-
-enum parser_rr_type {
-	PARSER_RRTYPE_UNKNOWN, /*!< 0 - an unknown type */
-	PARSER_RRTYPE_A, /*!< 1 - a host address */
-	PARSER_RRTYPE_NS, /*!< 2 - an authoritative name server */
-	PARSER_RRTYPE_MD, /*!< 3 - a mail destination (Obsolete - use MX) */
-	PARSER_RRTYPE_MF, /*!< 4 - a mail forwarder (Obsolete - use MX) */
-	PARSER_RRTYPE_CNAME, /*!< 5 - the canonical name for an alias */
-	PARSER_RRTYPE_SOA, /*!< 6 - marks the start of a zone of authority */
-	PARSER_RRTYPE_MB, /*!< 7 - a mailbox domain name (EXPERIMENTAL) */
-	PARSER_RRTYPE_MG, /*!< 8 - a mail group member (EXPERIMENTAL) */
-	PARSER_RRTYPE_MR, /*!< 9 - a mail rename domain name (EXPERIMENTAL) */
-	PARSER_RRTYPE_NULL, /*!< 10 - a null RR (EXPERIMENTAL) */
-	PARSER_RRTYPE_WKS, /*!< 11 - a well known service description */
-	PARSER_RRTYPE_PTR, /*!< 12 - a domain name pointer */
-	PARSER_RRTYPE_HINFO, /*!< 13 - host information */
-	PARSER_RRTYPE_MINFO, /*!< 14 - mailbox or mail list information */
-	PARSER_RRTYPE_MX, /*!< 15 - mail exchange */
-	PARSER_RRTYPE_TXT, /*!< 16 - text strings */
-	PARSER_RRTYPE_RP, /*!< 17 - RFC1183 */
-	PARSER_RRTYPE_AFSDB, /*!< 18 - RFC1183 */
-	PARSER_RRTYPE_X25, /*!< 19 - RFC1183 */
-	PARSER_RRTYPE_ISDN, /*!< 20 - RFC1183 */
-	PARSER_RRTYPE_RT, /*!< 21 - RFC1183 */
-	PARSER_RRTYPE_NSAP, /*!< 22 - RFC1706 */
-
-	PARSER_RRTYPE_SIG = 24, /*!< 24 - 2535typecode */
-	PARSER_RRTYPE_KEY, /*!< 25 - 2535typecode */
-	PARSER_RRTYPE_PX, /*!< 26 - RFC2163 */
-
-	PARSER_RRTYPE_AAAA = 28, /*!< 28 - ipv6 address */
-	PARSER_RRTYPE_LOC, /*!< 29 - LOC record  RFC1876 */
-	PARSER_RRTYPE_NXT, /*!< 30 - 2535typecode */
-
-	PARSER_RRTYPE_SRV = 33, /*!< 33 - SRV record RFC2782 */
-
-	PARSER_RRTYPE_NAPTR = 35, /*!< 35 - RFC2915 */
-	PARSER_RRTYPE_KX, /*!< 36 - RFC2230 Key Exchange Delegation Record */
-	PARSER_RRTYPE_CERT, /*!< 37 - RFC2538 */
-	PARSER_RRTYPE_A6, /*!< 38 - RFC2874 */
-	PARSER_RRTYPE_DNAME, /*!< 39 - RFC2672 */
-
-	PARSER_RRTYPE_OPT = 41, /*!< 41 - Pseudo OPT record... */
-	PARSER_RRTYPE_APL, /*!< 42 - RFC3123 */
-	PARSER_RRTYPE_DS, /*!< 43 - RFC 4033, 4034, and 4035 */
-	PARSER_RRTYPE_SSHFP, /*!< 44 - SSH Key Fingerprint */
-	PARSER_RRTYPE_IPSECKEY, /*!< 45 - public key for ipsec use. RFC 4025 */
-	PARSER_RRTYPE_RRSIG, /*!< 46 - RFC 4033, 4034, and 4035 */
-	PARSER_RRTYPE_NSEC, /*!< 47 - RFC 4033, 4034, and 4035 */
-	PARSER_RRTYPE_DNSKEY, /*!< 48 - RFC 4033, 4034, and 4035 */
-	PARSER_RRTYPE_DHCID, /*!< 49 - RFC4701 DHCP information */
-	/*!
-	 * \brief 50 - NSEC3, secure denial, prevents zonewalking
-	 */
-	PARSER_RRTYPE_NSEC3,
-	/*!
-	 * \brief  51 - NSEC3PARAM at zone apex nsec3 parameters
-	 */
-	PARSER_RRTYPE_NSEC3PARAM, 
-	PARSER_RRTYPE_TLSA = 52,
-
-	/* TODO consider some better way of doing this, indices too high */
-
-	PARSER_RRTYPE_SPF = 99,      /*!< RFC 4408 */
-
-	// not designating any RRs
-	PARSER_RRTYPE_TSIG = 250,
-	PARSER_RRTYPE_IXFR = 251,
-	PARSER_RRTYPE_AXFR = 252,
-	/*!
-	 * \brief A request for mailbox-related records (MB, MG or MR)
-	 */
-	PARSER_RRTYPE_MAILB = 253,
-	/*!
-	 * \brief A request for mail agent RRs (Obsolete - see MX)
-	 */
-	PARSER_RRTYPE_MAILA = 254,
-	PARSER_RRTYPE_ANY = 255, /*!< any type (wildcard) */
-
-	// totally weird numbers (cannot use for indexing)
-	PARSER_RRTYPE_TA = 32768, /*!< DNSSEC Trust Authorities */
-	PARSER_RRTYPE_DLV = 32769, /*!< RFC 4431 */
-	PARSER_RRTYPE_TYPEXXX = 32770
-};
-
-/*!
- * \brief Enum containing RR type codes.
- *
- * \todo Not all indices can be used for indexing.
- */
-typedef enum parser_rr_type parser_rr_type_t;
-
-static uint const PARSER_RRTYPE_LAST = PARSER_RRTYPE_SPF;
-
-enum parser_rdata_wireformat {
-	/*!
-	 * \brief Possibly compressed domain name.
-	 */	
-	PARSER_RDATA_WF_COMPRESSED_DNAME = 50,
-	PARSER_RDATA_WF_UNCOMPRESSED_DNAME = 51, /*!< Uncompressed domain name.  */
-	PARSER_RDATA_WF_LITERAL_DNAME = 52, /*!< Literal (not downcased) dname.  */
-	PARSER_RDATA_WF_BYTE = 1, /*!< 8-bit integer.  */
-	PARSER_RDATA_WF_SHORT = 2, /*!< 16-bit integer.  */
-	PARSER_RDATA_WF_LONG = 4, /*!< 32-bit integer.  */
-	PARSER_RDATA_WF_TEXT = 53, /*!< Text string.  */
-	PARSER_RDATA_WF_A = 58, /*!< 32-bit IPv4 address.  */
-	PARSER_RDATA_WF_AAAA = 16, /*!< 128-bit IPv6 address.  */
-	PARSER_RDATA_WF_BINARY = 54, /*!< Binary data (unknown length).  */
-	/*!
-	 * \brief Binary data preceded by 1 byte length 
-	 */
-	PARSER_RDATA_WF_BINARYWITHLENGTH = 55,
-	PARSER_RDATA_WF_APL = 56, /*!< APL data.  */
-	PARSER_RDATA_WF_IPSECGATEWAY = 57 /*!< IPSECKEY gateway ip4, ip6 or dname. */
-};
-
-/*!
- * \brief Enum containing wireformat codes. Taken from NSD's "dns.h"
- */
-typedef enum parser_rdatawireformat parser_rdata_wireformat_t;
-
-struct parser_rrtype_descriptor {
-	uint16_t type;	/*!< RR type */
-	int token; /*< Token used in zoneparser */
-	const char *name;	/*!< Textual name.  */
-	uint8_t length;	/*!< Maximum number of RDATA items.  */
-	/*!
-	 * \brief rdata_wireformat_type
-	 */
-	uint8_t wireformat[PARSER_MAX_RDATA_ITEMS]; 
-	bool fixed_items; /*!< Has fixed number of RDATA items? */
-};
-
-/*!
- * \brief Structure holding RR descriptor
- */
-typedef struct parser_rrtype_descriptor parser_rrtype_descriptor_t;
-
-/*!
- * \brief Gets RR descriptor for given RR type.
- *
- * \param type Code of RR type whose descriptor should be returned.
- *
- * \return RR descriptor for given type code, NULL descriptor if
- *         unknown type.
- *
- * \todo Change return value to const.
- */
-parser_rrtype_descriptor_t *parser_rrtype_descriptor_by_type(uint16_t type);
-
-/*!
- * \brief Gets RR descriptor for given RR name.
- *
- * \param name Mnemonic of RR type whose descriptor should be returned.
- *
- * \return RR descriptor for given name, NULL descriptor if
- *         unknown type.
- *
- * \todo Change return value to const.
- */
-parser_rrtype_descriptor_t *parser_rrtype_descriptor_by_name(const char *name);
-
-/*!
- * \brief Converts numeric type representation to mnemonic string.
- *
- * \param rrtype Type RR type code to be converted.
- *
- * \return Mnemonic string if found, str(TYPE[rrtype]) otherwise.
- */
-const char *parser_rrtype_to_string(uint16_t rrtype);
-
-/*!
- * \brief Converts mnemonic string representation of a type to numeric one.
- *
- * \param name Mnemonic string to be converted.
- *
- * \return Correct code if found, 0 otherwise.
- */
-uint16_t parser_rrtype_from_string(const char *name);
-
-/*!
- * \brief Converts numeric class representation to string one.
- *
- * \param rrclass Class code to be converted.
- *
- * \return String represenation of class if found,
- *         str(CLASS[rrclass]) otherwise.
- */
-const char *parser_rrclass_to_string(uint16_t rrclass);
-
-/*!
- * \brief Converts string representation of a class to numeric one.
- *
- * \param name Class string to be converted.
- *
- * \return Correct code if found, 0 otherwise.
- */
-uint16_t parser_rrclass_from_string(const char *name);
-
-#endif /* _KNOTD_PARSER_DESCRIPTOR_H_ */
-
-/*! @} */
diff --git a/src/zcompile/parser-util.c b/src/zcompile/parser-util.c
deleted file mode 100644
index 9616ca29714d9609ac23aae4e956274e96cd0417..0000000000000000000000000000000000000000
--- a/src/zcompile/parser-util.c
+++ /dev/null
@@ -1,2474 +0,0 @@
-/*!
- * \file parser-util.c
- *
- * \author NLnet Labs
- *         Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * \brief utility functions for zone parser.
- *
- * \addtogroup zoneparser
- * @{
- */
-
-/*
- * Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * This software is open source.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- *
- * Neither the name of the NLNET LABS nor the names of its contributors may
- * be used to endorse or promote products derived from this software without
- * specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include <config.h>
-#include <assert.h>
-#include <fcntl.h>
-#include <ctype.h>
-#include <errno.h>
-#include <limits.h>
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-#include <stdlib.h>
-#include <time.h>
-#include <netinet/in.h>
-#include <sys/socket.h>
-#include <netdb.h>
-
-//#include "common.h"
-#include "common/base32hex.h"
-#include "zcompile/parser-util.h"
-#include "zcompile/zcompile.h"
-#include "parser-descriptor.h"
-#include "libknot/util/utils.h"
-#include "zcompile/zcompile-error.h"
-
-#define IP6ADDRLEN	(128/8)
-#define	NS_INT16SZ	2
-#define NS_INADDRSZ 4
-#define NS_IN6ADDRSZ 16
-#define APL_NEGATION_MASK      0x80U
-
-/* int
- * inet_pton(af, src, dst)
- *	convert from presentation format (which usually means ASCII printable)
- *	to network format (which is usually some kind of binary format).
- * return:
- *	1 if the address was valid for the specified address family
- *	0 if the address wasn't valid (`dst' is untouched in this case)
- *	-1 if some other error occurred (`dst' is untouched in this case, too)
- * author:
- *	Paul Vixie, 1996.
- */
-int inet_pton(int af, const char *src, void *dst)
-{
-	switch (af) {
-	case AF_INET:
-		return (inet_pton4(src, dst));
-	case AF_INET6:
-		return (inet_pton6(src, dst));
-	default:
-		errno = EAFNOSUPPORT;
-		return (-1);
-	}
-	/* NOTREACHED */
-}
-
-//int my_b32_pton(const char *src, uint8_t *target, size_t tsize)
-//{
-//	char ch;
-//	size_t p = 0;
-
-//	memset(target, '\0', tsize);
-//	while ((ch = *src++)) {
-//		uint8_t d;
-//		size_t b;
-//		size_t n;
-
-//		if (p + 5 >= tsize * 8) {
-//			return -1;
-//		}
-
-//		if (isspace(ch)) {
-//			continue;
-//		}
-
-//		if (ch >= '0' && ch <= '9') {
-//			d = ch - '0';
-//		} else if (ch >= 'A' && ch <= 'V') {
-//			d = ch - 'A' + 10;
-//		} else if (ch >= 'a' && ch <= 'v') {
-//			d = ch - 'a' + 10;
-//		} else {
-//			return -1;
-//		}
-
-//		b = 7 - p % 8;
-//		n = p / 8;
-
-//		if (b >= 4) {
-//			target[n] |= d << (b - 4);
-//		} else {
-//			target[n] |= d >> (4 - b);
-//			target[n+1] |= d << (b + 4);
-//		}
-//		p += 5;
-//	}
-//	return (p + 7) / 8;
-//}
-
-
-#define Assert(Cond) if (!(Cond)) abort()
-
-static const char Base64[] =
-	"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
-static const char Pad64 = '=';
-
-/* int
- * inet_pton4(src, dst)
- *	like inet_aton() but without all the hexadecimal and shorthand.
- * return:
- *	1 if `src' is a valid dotted quad, else 0.
- * notice:
- *	does not touch `dst' unless it's returning 1.
- * author:
- *	Paul Vixie, 1996.
- */
-int inet_pton4(const char *src, uint8_t *dst)
-{
-	static const char digits[] = "0123456789";
-	int saw_digit, octets, ch;
-	uint8_t tmp[NS_INADDRSZ], *tp;
-
-	saw_digit = 0;
-	octets = 0;
-	*(tp = tmp) = 0;
-	while ((ch = *src++) != '\0') {
-		const char *pch;
-
-		if ((pch = strchr(digits, ch)) != NULL) {
-			uint32_t new = *tp * 10 + (pch - digits);
-
-			if (new > 255) {
-				return (0);
-			}
-			*tp = new;
-			if (! saw_digit) {
-				if (++octets > 4) {
-					return (0);
-				}
-				saw_digit = 1;
-			}
-		} else if (ch == '.' && saw_digit) {
-			if (octets == 4) {
-				return (0);
-			}
-			*++tp = 0;
-			saw_digit = 0;
-		} else {
-			return (0);
-		}
-	}
-	if (octets < 4) {
-		return (0);
-	}
-
-	memcpy(dst, tmp, NS_INADDRSZ);
-	return (1);
-}
-
-/* int
- * inet_pton6(src, dst)
- *	convert presentation level address to network order binary form.
- * return:
- *	1 if `src' is a valid [RFC1884 2.2] address, else 0.
- * notice:
- *	(1) does not touch `dst' unless it's returning 1.
- *	(2) :: in a full address is silently ignored.
- * credit:
- *	inspired by Mark Andrews.
- * author:
- *	Paul Vixie, 1996.
- */
-int inet_pton6(const char *src, uint8_t *dst)
-{
-	static const char xdigits_l[] = "0123456789abcdef",
-					xdigits_u[] = "0123456789ABCDEF";
-	uint8_t tmp[NS_IN6ADDRSZ], *tp, *endp, *colonp;
-	const char *xdigits, *curtok;
-	int ch, saw_xdigit;
-	uint32_t val;
-
-	memset((tp = tmp), '\0', NS_IN6ADDRSZ);
-	endp = tp + NS_IN6ADDRSZ;
-	colonp = NULL;
-	/* Leading :: requires some special handling. */
-	if (*src == ':')
-		if (*++src != ':') {
-			return (0);
-		}
-	curtok = src;
-	saw_xdigit = 0;
-	val = 0;
-	while ((ch = *src++) != '\0') {
-		const char *pch;
-
-		if ((pch = strchr((xdigits = xdigits_l), ch)) == NULL) {
-			pch = strchr((xdigits = xdigits_u), ch);
-		}
-		if (pch != NULL) {
-			val <<= 4;
-			val |= (pch - xdigits);
-			if (val > 0xffff) {
-				return (0);
-			}
-			saw_xdigit = 1;
-			continue;
-		}
-		if (ch == ':') {
-			curtok = src;
-			if (!saw_xdigit) {
-				if (colonp) {
-					return (0);
-				}
-				colonp = tp;
-				continue;
-			}
-			if (tp + NS_INT16SZ > endp) {
-				return (0);
-			}
-			*tp++ = (uint8_t)(val >> 8) & 0xff;
-			*tp++ = (uint8_t) val & 0xff;
-			saw_xdigit = 0;
-			val = 0;
-			continue;
-		}
-		if (ch == '.' && ((tp + NS_INADDRSZ) <= endp) &&
-				inet_pton4(curtok, tp) > 0) {
-			tp += NS_INADDRSZ;
-			saw_xdigit = 0;
-			break;	/* '\0' was seen by inet_pton4(). */
-		}
-		return (0);
-	}
-	if (saw_xdigit) {
-		if (tp + NS_INT16SZ > endp) {
-			return (0);
-		}
-		*tp++ = (uint8_t)(val >> 8) & 0xff;
-		*tp++ = (uint8_t) val & 0xff;
-	}
-	if (colonp != NULL) {
-		/*
-		 * Since some memmove()'s erroneously fail to handle
-		 * overlapping regions, we'll do the shift by hand.
-		 */
-		const int n = tp - colonp;
-		int i;
-
-		for (i = 1; i <= n; i++) {
-			endp[- i] = colonp[n - i];
-			colonp[n - i] = 0;
-		}
-		tp = endp;
-	}
-	if (tp != endp) {
-		return (0);
-	}
-	memcpy(dst, tmp, NS_IN6ADDRSZ);
-	return (1);
-}
-
-
-#ifndef IN6ADDRSZ
-#define IN6ADDRSZ   16   /* IPv6 T_AAAA */
-#endif
-
-#ifndef INT16SZ
-#define INT16SZ     2    /* for systems without 16-bit ints */
-#endif
-
-/*
- * WARNING: Don't even consider trying to compile this on a system where
- * sizeof(int) < 4.  sizeof(int) > 4 is fine; all the world's not a VAX.
- */
-
-
-/* char *
- * inet_ntop(af, src, dst, size)
- *	convert a network format address to presentation format.
- * return:
- *	pointer to presentation format address (`dst'), or NULL (see errno).
- * author:
- *	Paul Vixie, 1996.
- */
-//const char *inet_ntop(int af, const void *src, char *dst, size_t size)
-//{
-//	switch (af) {
-//	case AF_INET:
-//		return (inet_ntop4(src, dst, size));
-//	case AF_INET6:
-//		return (inet_ntop6(src, dst, size));
-//	default:
-//		errno = EAFNOSUPPORT;
-//		return (NULL);
-//	}
-//	/* NOTREACHED */
-//}
-
-/* const char *
- * inet_ntop4(src, dst, size)
- *	format an IPv4 address, more or less like inet_ntoa()
- * return:
- *	`dst' (as a const)
- * notes:
- *	(1) uses no statics
- *	(2) takes a u_char* not an in_addr as input
- * author:
- *	Paul Vixie, 1996.
- */
-const char *inet_ntop4(const u_char *src, char *dst, size_t size)
-{
-	static const char fmt[] = "%u.%u.%u.%u";
-	char tmp[sizeof "255.255.255.255"];
-	int l;
-
-	l = snprintf(tmp, size, fmt, src[0], src[1], src[2], src[3]);
-	if (l <= 0 || l >= (int)size) {
-		errno = ENOSPC;
-		return (NULL);
-	}
-	knot_strlcpy(dst, tmp, size);
-	return (dst);
-}
-
-/* const char *
- * inet_ntop6(src, dst, size)
- *	convert IPv6 binary address into presentation (printable) format
- * author:
- *	Paul Vixie, 1996.
- */
-const char *inet_ntop6(const u_char *src, char *dst, size_t size)
-{
-	/*
-	 * Note that int32_t and int16_t need only be "at least" large enough
-	 * to contain a value of the specified size.  On some systems, like
-	 * Crays, there is no such thing as an integer variable with 16 bits.
-	 * Keep this in mind if you think this function should have been coded
-	 * to use pointer overlays.  All the world's not a VAX.
-	 */
-	char tmp[sizeof "ffff:ffff:ffff:ffff:ffff:ffff:255.255.255.255"];
-	char *tp, *ep;
-	struct {
-		int base, len;
-	} best, cur;
-	best.base = cur.base =-1;
-	best.len = cur.len = 0;
-	u_int words[IN6ADDRSZ / INT16SZ];
-	int i;
-	int advance;
-
-	/*
-	 * Preprocess:
-	 *	Copy the input (bytewise) array into a wordwise array.
-	 *	Find the longest run of 0x00's in src[] for :: shorthanding.
-	 */
-	memset(words, '\0', sizeof words);
-	for (i = 0; i < IN6ADDRSZ; i++) {
-		words[i / 2] |= (src[i] << ((1 - (i % 2)) << 3));
-	}
-
-	for (i = 0; i < (IN6ADDRSZ / INT16SZ); i++) {
-		if (words[i] == 0) {
-			if (cur.base == -1) {
-				cur.base = i, cur.len = 1;
-			} else {
-				cur.len++;
-			}
-		} else {
-			if (cur.base != -1) {
-				if (best.base == -1 || cur.len > best.len) {
-					best = cur;
-				}
-				cur.base = -1;
-			}
-		}
-	}
-	if (cur.base != -1) {
-		if (best.base == -1 || cur.len > best.len) {
-			best = cur;
-		}
-	}
-	if (best.base != -1 && best.len < 2) {
-		best.base = -1;
-	}
-
-	/*
-	 * Format the result.
-	 */
-	tp = tmp;
-	ep = tmp + sizeof(tmp);
-	for (i = 0; i < (IN6ADDRSZ / INT16SZ) && tp < ep; i++) {
-		/* Are we inside the best run of 0x00's? */
-		if (best.base != -1 && i >= best.base &&
-				i < (best.base + best.len)) {
-			if (i == best.base) {
-				if (tp + 1 >= ep) {
-					return (NULL);
-				}
-				*tp++ = ':';
-			}
-			continue;
-		}
-		/* Are we following an initial run of 0x00s or any real hex? */
-		if (i != 0) {
-			if (tp + 1 >= ep) {
-				return (NULL);
-			}
-			*tp++ = ':';
-		}
-		/* Is this address an encapsulated IPv4? */
-		if (i == 6 && best.base == 0 &&
-				(best.len == 6 ||
-				(best.len == 5 && words[5] == 0xffff))) {
-			if (!inet_ntop4(src + 12, tp, (size_t)(ep - tp))) {
-				return (NULL);
-			}
-			tp += strlen(tp);
-			break;
-		}
-		advance = snprintf(tp, ep - tp, "%x", words[i]);
-		if (advance <= 0 || advance >= ep - tp) {
-			return (NULL);
-		}
-		tp += advance;
-	}
-	/* Was it a trailing run of 0x00's? */
-	if (best.base != -1 && (best.base + best.len) ==
-	   (IN6ADDRSZ / INT16SZ)) {
-		if (tp + 1 >= ep) {
-			return (NULL);
-		}
-		*tp++ = ':';
-	}
-	if (tp + 1 >= ep) {
-		return (NULL);
-	}
-	*tp++ = '\0';
-
-	/*
-	 * Check for overflow, copy, and we're done.
-	 */
-	if ((size_t)(tp - tmp) > size) {
-		errno = ENOSPC;
-		return (NULL);
-	}
-	knot_strlcpy(dst, tmp, size);
-	return (dst);
-}
-
-
-static int b64rmap_initialized = 0;
-static uint8_t b64rmap[256];
-
-static const uint8_t b64rmap_special = 0xf0;
-static const uint8_t b64rmap_end = 0xfd;
-static const uint8_t b64rmap_space = 0xfe;
-static const uint8_t b64rmap_invalid = 0xff;
-
-/**
- * Initializing the reverse map is not thread safe.
- * Which is fine for NSD. For now...
- **/
-void b64_initialize_rmap()
-{
-	int i;
-	char ch;
-
-	/* Null: end of string, stop parsing */
-	b64rmap[0] = b64rmap_end;
-
-	for (i = 1; i < 256; ++i) {
-		ch = (char)i;
-		/* Whitespaces */
-		if (isspace(ch)) {
-			b64rmap[i] = b64rmap_space;
-		}
-		/* Padding: stop parsing */
-		else if (ch == Pad64) {
-			b64rmap[i] = b64rmap_end;
-		}
-		/* Non-base64 char */
-		else {
-			b64rmap[i] = b64rmap_invalid;
-		}
-	}
-
-	/* Fill reverse mapping for base64 chars */
-	for (i = 0; Base64[i] != '\0'; ++i) {
-		b64rmap[(uint8_t)Base64[i]] = i;
-	}
-
-	b64rmap_initialized = 1;
-}
-
-int b64_pton_do(char const *src, uint8_t *target, size_t targsize)
-{
-	int tarindex, state, ch;
-	uint8_t ofs;
-
-	state = 0;
-	tarindex = 0;
-
-	while (1) {
-		ch = *src++;
-		ofs = b64rmap[ch];
-
-		if (ofs >= b64rmap_special) {
-			/* Ignore whitespaces */
-			if (ofs == b64rmap_space) {
-				continue;
-			}
-			/* End of base64 characters */
-			if (ofs == b64rmap_end) {
-				break;
-			}
-			/* A non-base64 character. */
-			return (-1);
-		}
-
-		switch (state) {
-		case 0:
-			if ((size_t)tarindex >= targsize) {
-				return (-1);
-			}
-			target[tarindex] = ofs << 2;
-			state = 1;
-			break;
-		case 1:
-			if ((size_t)tarindex + 1 >= targsize) {
-				return (-1);
-			}
-			target[tarindex]   |=  ofs >> 4;
-			target[tarindex+1]  = (ofs & 0x0f)
-					      << 4 ;
-			tarindex++;
-			state = 2;
-			break;
-		case 2:
-			if ((size_t)tarindex + 1 >= targsize) {
-				return (-1);
-			}
-			target[tarindex]   |=  ofs >> 2;
-			target[tarindex+1]  = (ofs & 0x03)
-					      << 6;
-			tarindex++;
-			state = 3;
-			break;
-		case 3:
-			if ((size_t)tarindex >= targsize) {
-				return (-1);
-			}
-			target[tarindex] |= ofs;
-			tarindex++;
-			state = 0;
-			break;
-		default:
-			abort();
-		}
-	}
-
-	/*
-	 * We are done decoding Base-64 chars.  Let's see if we ended
-	 * on a byte boundary, and/or with erroneous trailing characters.
-	 */
-
-	if (ch == Pad64) {		/* We got a pad char. */
-		ch = *src++;		/* Skip it, get next. */
-		switch (state) {
-		case 0:		/* Invalid = in first position */
-		case 1:		/* Invalid = in second position */
-			return (-1);
-
-		case 2:		/* Valid, means one byte of info */
-			/* Skip any number of spaces. */
-			for ((void)NULL; ch != '\0'; ch = *src++)
-				if (b64rmap[ch] != b64rmap_space) {
-					break;
-				}
-			/* Make sure there is another trailing = sign. */
-			if (ch != Pad64) {
-				return (-1);
-			}
-			ch = *src++;		/* Skip the = */
-			/* Fall through to "single trailing =" case. */
-			/* FALLTHROUGH */
-
-		case 3:		/* Valid, means two bytes of info */
-			/*
-			 * We know this char is an =.  Is there anything but
-			 * whitespace after it?
-			 */
-			for ((void)NULL; ch != '\0'; ch = *src++)
-				if (b64rmap[ch] != b64rmap_space) {
-					return (-1);
-				}
-
-			/*
-			 * Now make sure for cases 2 and 3 that the "extra"
-			 * bits that slopped past the last full byte were
-			 * zeros.  If we don't check them, they become a
-			 * subliminal channel.
-			 */
-			if (target[tarindex] != 0) {
-				return (-1);
-			}
-		}
-	} else {
-		/*
-		 * We ended by seeing the end of the string.  Make sure we
-		 * have no partial bytes lying around.
-		 */
-		if (state != 0) {
-			return (-1);
-		}
-	}
-
-	return (tarindex);
-}
-
-
-int b64_pton_len(char const *src)
-{
-	int tarindex, state, ch;
-	uint8_t ofs;
-
-	state = 0;
-	tarindex = 0;
-
-	while (1) {
-		ch = *src++;
-		ofs = b64rmap[ch];
-
-		if (ofs >= b64rmap_special) {
-			/* Ignore whitespaces */
-			if (ofs == b64rmap_space) {
-				continue;
-			}
-			/* End of base64 characters */
-			if (ofs == b64rmap_end) {
-				break;
-			}
-			/* A non-base64 character. */
-			return (-1);
-		}
-
-		switch (state) {
-		case 0:
-			state = 1;
-			break;
-		case 1:
-			tarindex++;
-			state = 2;
-			break;
-		case 2:
-			tarindex++;
-			state = 3;
-			break;
-		case 3:
-			tarindex++;
-			state = 0;
-			break;
-		default:
-			abort();
-		}
-	}
-
-	/*
-	 * We are done decoding Base-64 chars.  Let's see if we ended
-	 * on a byte boundary, and/or with erroneous trailing characters.
-	 */
-
-	if (ch == Pad64) {		/* We got a pad char. */
-		ch = *src++;		/* Skip it, get next. */
-		switch (state) {
-		case 0:		/* Invalid = in first position */
-		case 1:		/* Invalid = in second position */
-			return (-1);
-
-		case 2:		/* Valid, means one byte of info */
-			/* Skip any number of spaces. */
-			for ((void)NULL; ch != '\0'; ch = *src++)
-				if (b64rmap[ch] != b64rmap_space) {
-					break;
-				}
-			/* Make sure there is another trailing = sign. */
-			if (ch != Pad64) {
-				return (-1);
-			}
-			ch = *src++;		/* Skip the = */
-			/* Fall through to "single trailing =" case. */
-			/* FALLTHROUGH */
-
-		case 3:		/* Valid, means two bytes of info */
-			/*
-			 * We know this char is an =.  Is there anything but
-			 * whitespace after it?
-			 */
-			for ((void)NULL; ch != '\0'; ch = *src++)
-				if (b64rmap[ch] != b64rmap_space) {
-					return (-1);
-				}
-
-		}
-	} else {
-		/*
-		 * We ended by seeing the end of the string.  Make sure we
-		 * have no partial bytes lying around.
-		 */
-		if (state != 0) {
-			return (-1);
-		}
-	}
-
-	return (tarindex);
-}
-
-int b64_pton(char const *src, uint8_t *target, size_t targsize)
-{
-	if (!b64rmap_initialized) {
-		b64_initialize_rmap();
-	}
-
-	if (target) {
-		return b64_pton_do(src, target, targsize);
-	} else {
-		return b64_pton_len(src);
-	}
-}
-
-void set_bit(uint8_t bits[], size_t index)
-{
-	/*
-	 * The bits are counted from left to right, so bit #0 is the
-	 * left most bit.
-	 */
-	bits[index / 8] |= (1 << (7 - index % 8));
-}
-
-uint32_t strtoserial(const char *nptr, const char **endptr)
-{
-	uint32_t i = 0;
-	uint32_t serial = 0;
-
-	for (*endptr = nptr; **endptr; (*endptr)++) {
-		switch (**endptr) {
-		case ' ':
-		case '\t':
-			break;
-		case '0':
-		case '1':
-		case '2':
-		case '3':
-		case '4':
-		case '5':
-		case '6':
-		case '7':
-		case '8':
-		case '9':
-			i *= 10;
-			i += (**endptr - '0');
-			break;
-		default:
-			break;
-		}
-	}
-	serial += i;
-	return serial;
-}
-
-inline void write_uint32(void *dst, uint32_t data)
-{
-/*!< \todo Check what this means and delete if obsolete. */
-#ifdef ALLOW_UNALIGNED_ACCESSES
-	*(uint32_t *) dst = htonl(data);
-#else
-	uint8_t *p = (uint8_t *) dst;
-	p[0] = (uint8_t)((data >> 24) & 0xff);
-	p[1] = (uint8_t)((data >> 16) & 0xff);
-	p[2] = (uint8_t)((data >> 8) & 0xff);
-	p[3] = (uint8_t)(data & 0xff);
-#endif
-}
-
-uint32_t strtottl(const char *nptr, const char **endptr)
-{
-	uint32_t i = 0;
-	uint32_t seconds = 0;
-
-	for (*endptr = nptr; **endptr; (*endptr)++) {
-		switch (**endptr) {
-		case ' ':
-		case '\t':
-			break;
-		case 's':
-		case 'S':
-			seconds += i;
-			i = 0;
-			break;
-		case 'm':
-		case 'M':
-			seconds += i * 60;
-			i = 0;
-			break;
-		case 'h':
-		case 'H':
-			seconds += i * 60 * 60;
-			i = 0;
-			break;
-		case 'd':
-		case 'D':
-			seconds += i * 60 * 60 * 24;
-			i = 0;
-			break;
-		case 'w':
-		case 'W':
-			seconds += i * 60 * 60 * 24 * 7;
-			i = 0;
-			break;
-		case '0':
-		case '1':
-		case '2':
-		case '3':
-		case '4':
-		case '5':
-		case '6':
-		case '7':
-		case '8':
-		case '9':
-			i *= 10;
-			i += (**endptr - '0');
-			break;
-		default:
-			seconds += i;
-			return seconds;
-		}
-	}
-	seconds += i;
-	return seconds;
-}
-
-/* Number of days per month (except for February in leap years). */
-static const int mdays[] = {
-    31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
-};
-
-static int is_leap_year(int year)
-{
-    return year % 4 == 0 && (year % 100 != 0 || year % 400 == 0);
-}
-
-static int leap_days(int y1, int y2)
-{
-    --y1;
-    --y2;
-    return (y2/4 - y1/4) - (y2/100 - y1/100) + (y2/400 - y1/400);
-}
-
-/*
- * Code adapted from Python 2.4.1 sources (Lib/calendar.py).
- */
-time_t mktime_from_utc(const struct tm *tm)
-{
-    int year = 1900 + tm->tm_year;
-    time_t days = 365 * (year - 1970) + leap_days(1970, year);
-    time_t hours;
-    time_t minutes;
-    time_t seconds;
-    int i;
-
-    for (i = 0; i < tm->tm_mon; ++i) {
-	days += mdays[i];
-    }
-    if (tm->tm_mon > 1 && is_leap_year(year)) {
-	++days;
-    }
-    days += tm->tm_mday - 1;
-
-    hours = days * 24 + tm->tm_hour;
-    minutes = hours * 60 + tm->tm_min;
-    seconds = minutes * 60 + tm->tm_sec;
-
-    return seconds;
-}
-
-/*!< Following functions are conversions from text to wire. */
-//#define DEBUG_UNKNOWN_RDATA
-
-#ifdef DEBUG_UNKNOWN_RDATA
-#define dbg_rdata(msg...) fprintf(stderr, msg)
-#define DBG_RDATA(cmds) do { cmds } while (0)
-#else
-#define dbg_rdata(msg...)
-#define DBG_RDATA(cmds)
-#endif
-
-
-
-#define IP6ADDRLEN	(128/8)
-#define	NS_INT16SZ	2
-#define NS_INADDRSZ 4
-#define NS_IN6ADDRSZ 16
-#define APL_NEGATION_MASK      0x80U
-#define APL_LENGTH_MASK	       (~APL_NEGATION_MASK)
-
-//#define ZP_DEBUG
-
-#ifdef ZP_DEBUG
-#define dbg_zp(msg...) fprintf(stderr, msg)
-#else
-#define dbg_zp(msg...)
-#endif
-
-
-/*!
- * \brief Return data of raw data item.
- *
- * \param item Item.
- * \return uint16_t * Raw data.
- */
-static inline uint16_t * rdata_atom_data(knot_rdata_item_t item)
-{
-	return (uint16_t *)(item.raw_data + 1);
-}
-
-/*!
- * \brief Return type of RRSet covered by given RRSIG.
- *
- * \param rrset RRSIG.
- * \return uint16_t Type covered.
- */
-uint16_t rrsig_type_covered(knot_rrset_t *rrset)
-{
-	assert(rrset->rdata->items[0].raw_data[0] == sizeof(uint16_t));
-
-	return ntohs(*(uint16_t *) rdata_atom_data(rrset->rdata->items[0]));
-}
-
-/*!
- * \brief Checks if item contains domain.
- *
- * \param type Type of RRSet.
- * \param index Index to check.
- *
- * \return > 1 if item is domain, 0 otherwise.
- */
-static inline int rdata_atom_is_domain(uint16_t type, size_t index)
-{
-	const knot_rrtype_descriptor_t *descriptor
-	= knot_rrtype_descriptor_by_type(type);
-	return (index < descriptor->length
-		&& (descriptor->wireformat[index] ==
-		KNOT_RDATA_WF_COMPRESSED_DNAME  ||
-		descriptor->wireformat[index] ==
-		KNOT_RDATA_WF_LITERAL_DNAME  ||
-		descriptor->wireformat[index] ==
-		KNOT_RDATA_WF_UNCOMPRESSED_DNAME));
-}
-
-/*!
- * \brief Returns which wireformat type is on given index.
- *
- * \param type Type of RRSet.
- * \param index Index.
- *
- * \return uint8_t Wireformat type.
- */
-static inline uint8_t rdata_atom_wireformat_type(uint16_t type, size_t index)
-{
-	const knot_rrtype_descriptor_t *descriptor =
-		knot_rrtype_descriptor_by_type(type);
-	assert(index < descriptor->length);
-	return descriptor->wireformat[index];
-}
-
-typedef int (*printf_t)(const char *fmt, ...);
-
-/*!
- * \brief Converts rdata wireformat to rdata items.
- *
- * \param wireformat Wireformat/.
- * \param rrtype RR type.
- * \param data_size Size of wireformat.
- * \param items created rdata items.
- *
- * \return Number of items converted.
- */
-static ssize_t rdata_wireformat_to_rdata_atoms(const uint16_t *wireformat,
-					uint16_t rrtype,
-					const uint16_t data_size,
-					knot_rdata_item_t **items)
-{
-	/*!< \todo This is so ugly, it makes me wanna puke. */
-	uint16_t const *end =
-		(uint16_t *)((uint8_t *)wireformat + (data_size));
-	dbg_rdata("set end pointer: %p which means length: %d\n", end,
-	          (uint8_t *)end - (uint8_t *)wireformat);
-	dbg_rdata("Parsing following wf: ");
-	size_t i;
-	knot_rdata_item_t *temp_rdatas =
-		malloc(sizeof(*temp_rdatas) * MAXRDATALEN);
-	if (temp_rdatas == NULL) {
-		ERR_ALLOC_FAILED;
-		return KNOTDZCOMPILE_ENOMEM;
-	}
-	memset(temp_rdatas, 0, sizeof(*temp_rdatas) * MAXRDATALEN);
-
-	knot_rrtype_descriptor_t *descriptor =
-		knot_rrtype_descriptor_by_type(rrtype);
-
-	assert(descriptor->length <= MAXRDATALEN);
-
-	dbg_rdata("will be parsing %d items, total size: %d\n",
-	          descriptor->length, data_size);
-
-	for (i = 0; i < descriptor->length; ++i) {
-		dbg_rdata("this particular item is type %d.\n",
-		          rdata_atom_wireformat_type(rrtype, i));
-		int is_domain = 0;
-		int is_wirestore = 0;
-		size_t length = 0;
-		length = 0;
-		bool required = descriptor->fixed_items;
-
-		switch (rdata_atom_wireformat_type(rrtype, i)) {
-		case KNOT_RDATA_WF_COMPRESSED_DNAME:
-		case KNOT_RDATA_WF_UNCOMPRESSED_DNAME:
-			dbg_rdata("Parsed item is a dname.\n");
-			is_domain = 1;
-			break;
-		case KNOT_RDATA_WF_LITERAL_DNAME:
-			dbg_rdata("Parsed item is a literal dname.\n");
-			is_domain = 1;
-			is_wirestore = 1;
-			break;
-		case KNOT_RDATA_WF_BYTE:
-			dbg_rdata("Parsed item is a byte.\n");
-			length = sizeof(uint8_t);
-			break;
-		case KNOT_RDATA_WF_SHORT:
-			dbg_rdata("Parsed item is a short.\n");
-			length = sizeof(uint16_t);
-			break;
-		case KNOT_RDATA_WF_LONG:
-			dbg_rdata("Parsed item is a long.\n");
-			length = sizeof(uint32_t);
-			break;
-		case KNOT_RDATA_WF_APL:
-			dbg_rdata("APL data.\n");
-		case KNOT_RDATA_WF_TEXT_SINGLE:
-		case KNOT_RDATA_WF_TEXT:
-			dbg_rdata("TEXT rdata.\n");
-		case KNOT_RDATA_WF_BINARYWITHLENGTH:
-			dbg_rdata("BINARYWITHLENGTH rdata.\n");
-			/* Length is stored in the first byte.  */
-			length = data_size;
-			break;
-		case KNOT_RDATA_WF_A:
-			dbg_rdata("Parsed item is an IPv4 address.\n");
-			length = sizeof(in_addr_t);
-			break;
-		case KNOT_RDATA_WF_AAAA:
-			dbg_rdata("Parsed item is an IPv6 address.\n");
-			length = IP6ADDRLEN;
-			break;
-		case KNOT_RDATA_WF_BINARY:
-			/* Remaining RDATA is binary.  */
-			dbg_rdata("BINARY: item %d: guessing length from pointers: %p %p. ",
-			          i,
-			          wireformat, end);
-			length = (uint8_t *)end - (uint8_t *)wireformat;
-			dbg_rdata("Result: %d.\n",
-			          length);
-			break;
-//		case KNOT_RDATA_WF_APL:
-//			length = (sizeof(uint16_t)    /* address family */
-//				  + sizeof(uint8_t)   /* prefix */
-//				  + sizeof(uint8_t)); /* length */
-//			if ((uint8_t *)wireformat + length <= (uint8_t *)end) {
-//				/* Mask out negation bit.  */
-//				dbg_rdata("APL: length was %d. ", length);
-//				length += (wireformat[data_size - 1]
-//					   & APL_LENGTH_MASK);
-//				dbg_rdata("APL: after masking: %d.\n", length);
-//			}
-//			break;
-		case KNOT_RDATA_WF_IPSECGATEWAY:
-			dbg_rdata("Parsed item is an IPSECGATEWAY address.\n");
-			dbg_rdata("Gateway type: %d\n",
-			          ((uint8_t *)rdata_atom_data(temp_rdatas[1]))[0]);
-			switch (((uint8_t *)rdata_atom_data(temp_rdatas[1]))[0]) {
-			/* gateway type */
-			case IPSECKEY_NOGATEWAY:
-				dbg_rdata("NOGATEWAY\n");
-				length = 0;
-				break;
-			case IPSECKEY_IP4:
-				dbg_rdata("IPv4\n");
-				length = 4;
-				break;
-			case IPSECKEY_IP6:
-				dbg_rdata("IPv6\n");
-				length = IP6ADDRLEN;
-				break;
-			case IPSECKEY_DNAME:
-				dbg_rdata("DNAME\n");
-				is_domain = 1;
-				is_wirestore = 1;
-				break;
-			default:
-				dbg_rdata("Unknown IPSECKEY gateway!\n");
-				free(temp_rdatas);
-				return -1;
-			} // switch
-		}
-
-		if (is_domain) {
-			knot_dname_t *dname = NULL;
-			/*
-			 * Since we don't know how many dnames there are 
-			 * in the whole wireformat we have to search for next
-			 * '\0'.
-			 */
-			for (length = 0;
-			     (length < ((uint8_t *)end - (uint8_t *)wireformat))
-			     && (((uint8_t *)wireformat)[length] != '\0');
-			     length++) {
-				;
-			}
-			length++;
-			dbg_rdata("item %d: length derived from position of "
-			          "0: %d\n", i, length);
-
-			if (!required && (wireformat == end)) {
-				break;
-			}
-
-			dname = knot_dname_new_from_wire((uint8_t *)wireformat,
-							 length,
-							 NULL);
-
-			if (dname == NULL) {
-				dbg_rdata("malformed dname!\n");
-				/*! \todo rdata purge */
-				free(temp_rdatas);
-				return KNOTDZCOMPILE_EBRDATA;
-			}
-			
-			dbg_rdata("item %d: created dname: %s, length: %d\n", i,
-			          knot_dname_to_str(dname), length);
-
-			if (is_wirestore) {
-				/*temp_rdatas[i].raw_data =
-					(uint16_t *) region_alloc(
-				region, sizeof(uint16_t) + dname->name_size);
-				temp_rdatas[i].data[0] = dname->name_size;
-				memcpy(temp_rdatas[i].data+1, dname_name(dname),
-				dname->name_size); */
-				temp_rdatas[i].raw_data =
-					malloc(sizeof(uint16_t) +
-					       sizeof(uint8_t) * dname->size);
-				if (temp_rdatas[i].raw_data == NULL) {
-					ERR_ALLOC_FAILED;
-					free(temp_rdatas);
-					knot_dname_free(&dname);
-					return KNOTDZCOMPILE_ENOMEM;
-				}
-
-				temp_rdatas[i].raw_data[0] = dname->size;
-				memcpy(temp_rdatas[i].raw_data + 1,
-				       dname->name, dname->size);
-
-				knot_dname_release(dname);
-			} else {
-				temp_rdatas[i].dname = dname;
-			}
-
-		} else {
-			/*!< \todo This calculated length makes no sense! */
-			dbg_rdata("item %d :length: %d calculated: %d (%p %p)\n", i, length,
-			          end - wireformat,
-			          wireformat, end);
-			if ((uint8_t *)wireformat + length > (uint8_t *)end) {
-				if (required) {
-					/* Truncated RDATA.  */
-					free(temp_rdatas);
-					dbg_rdata("truncated rdata, end pointer is exceeded by %d octets.\n",
-					          (wireformat + length) - end);
-					return KNOTDZCOMPILE_EBRDATA;
-				} else {
-					break;
-				}
-			}
-
-			assert(wireformat <= end); /*!< \todo remove! */
-			dbg_rdata("calling init with: %p and length : %d\n",
-			          wireformat, length);
-			temp_rdatas[i].raw_data = alloc_rdata_init(wireformat,
-			                                           length);
-			if (temp_rdatas[i].raw_data == NULL) {
-				ERR_ALLOC_FAILED;
-				free(temp_rdatas);
-				return -1;
-			}
-
-		}
-		dbg_rdata("%d: adding length: %d (remaining: %d)\n", i, length,
-		          (uint8_t *)end - ((uint8_t *)wireformat + length));
-		wireformat = (uint16_t *)((uint8_t *)wireformat + length);
-		dbg_rdata("wire: %p\n", wireformat);
-		dbg_rdata("remaining now: %d\n",
-		          end - wireformat);
-	}
-
-	dbg_rdata("%p %p\n", wireformat, (uint8_t *)wireformat);
-
-	if (wireformat < end) {
-		/* Trailing garbage.  */
-		dbg_rdata("Garbage: w: %p e: %p %d\n", wireformat, end, end - wireformat);
-		free(temp_rdatas);
-		return KNOTDZCOMPILE_EBRDATA;
-	}
-
-	*items = temp_rdatas;
-	/*	*rdatas = (rdata_atom_type *) region_alloc_init(
-			region, temp_rdatas, i * sizeof(rdata_atom_type)); */
-	dbg_rdata("wf_to_rdata_atoms: Succesfully converted %d items.\n",
-	          i);
-	return (ssize_t)i;
-}
-
-/* Taken from RFC 2535, section 7.  */
-knot_lookup_table_t dns_algorithms[] = {
-	{ 1, "RSAMD5" },	/* RFC 2537 */
-	{ 2, "DH" },		/* RFC 2539 */
-	{ 3, "DSA" },		/* RFC 2536 */
-	{ 4, "ECC" },
-	{ 5, "RSASHA1" },	/* RFC 3110 */
-	{ 252, "INDIRECT" },
-	{ 253, "PRIVATEDNS" },
-	{ 254, "PRIVATEOID" },
-	{ 0, NULL }
-};
-
-/* Taken from RFC 4398, section 2.1.  */
-knot_lookup_table_t dns_certificate_types[] = {
-	/*	0		Reserved */
-	{ 1, "PKIX" },	/* X.509 as per PKIX */
-	{ 2, "SPKI" },	/* SPKI cert */
-	{ 3, "PGP" },	/* OpenPGP packet */
-	{ 4, "IPKIX" },	/* The URL of an X.509 data object */
-	{ 5, "ISPKI" },	/* The URL of an SPKI certificate */
-	{ 6, "IPGP" },	/* The fingerprint and URL of an OpenPGP packet */
-	{ 7, "ACPKIX" },	/* Attribute Certificate */
-	{ 8, "IACPKIX" },	/* The URL of an Attribute Certificate */
-	{ 253, "URI" },	/* URI private */
-	{ 254, "OID" },	/* OID private */
-	/*	255 		Reserved */
-	/* 	256-65279	Available for IANA assignment */
-	/*	65280-65534	Experimental */
-	/*	65535		Reserved */
-	{ 0, NULL }
-};
-
-/* Imported from lexer. */
-extern int hexdigit_to_int(char ch);
-
-extern uint8_t nsecbits[NSEC_WINDOW_COUNT][NSEC_WINDOW_BITS_SIZE];
-extern uint16_t nsec_highest_rcode;
-
-/*!
- * \brief Allocate SIZE+sizeof(uint16_t) bytes and store SIZE in the first
- *        element.  Return a pointer to the allocation.
- *
- * \param size How many bytes to allocate.
- */
-static uint16_t * alloc_rdata(size_t size)
-{
-	uint16_t *result = malloc(sizeof(uint16_t) + size);
-	*result = size;
-	return result;
-}
-
-uint16_t *alloc_rdata_init(const void *data, size_t size)
-{
-	uint16_t *result = malloc(sizeof(uint16_t) + size);
-	if (result == NULL) {
-		return NULL;
-	}
-	*result = size;
-	memcpy(result + 1, data, size);
-	return result;
-}
-
-/*
- * These are parser function for generic zone file stuff.
- */
-uint16_t * zparser_conv_hex(const char *hex, size_t len)
-{
-	/* convert a hex value to wireformat */
-	uint16_t *r = NULL;
-	uint8_t *t;
-	int i;
-
-	if (len % 2 != 0) {
-		zc_error_prev_line("number of hex digits "
-		                   "must be a multiple of 2");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else if (len > MAX_RDLENGTH * 2) {
-		zc_error_prev_line("hex data exceeds maximum rdata length (%d)",
-			MAX_RDLENGTH);
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		/* the length part */
-
-		r = alloc_rdata(len / 2);
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-		t = (uint8_t *)(r + 1);
-
-		/* Now process octet by octet... */
-		while (*hex) {
-			*t = 0;
-			for (i = 16; i >= 1; i -= 15) {
-				if (isxdigit((int)*hex)) {
-					*t += hexdigit_to_int(*hex) * i;
-				} else {
-					zc_error_prev_line(
-						"illegal hex character '%c'",
-						(int) *hex);
-					parser->error_occurred =
-						KNOTDZCOMPILE_EBRDATA;
-					free(r);
-					return NULL;
-				}
-				++hex;
-			}
-			++t;
-		}
-	}
-
-	return r;
-}
-
-/* convert hex, precede by a 1-byte length */
-uint16_t * zparser_conv_hex_length(const char *hex, size_t len)
-{
-	uint16_t *r = NULL;
-	uint8_t *t;
-	int i;
-	if (len % 2 != 0) {
-		zc_error_prev_line("number of hex digits must be a "
-		                   "multiple of 2");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else if (len > 255 * 2) {
-		zc_error_prev_line("hex data exceeds 255 bytes");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		uint8_t *l;
-
-		/* the length part */
-		r = alloc_rdata(len / 2 + 1);
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-
-		t = (uint8_t *)(r + 1);
-
-		l = t++;
-		*l = '\0';
-
-		/* Now process octet by octet... */
-		while (*hex) {
-			*t = 0;
-			for (i = 16; i >= 1; i -= 15) {
-				if (isxdigit((int)*hex)) {
-					*t += hexdigit_to_int(*hex) * i;
-				} else {
-					zc_error_prev_line(
-						"illegal hex character '%c'",
-						(int) *hex);
-					parser->error_occurred =
-						KNOTDZCOMPILE_EBRDATA;
-					free(r);
-					return NULL;
-				}
-				++hex;
-			}
-			++t;
-			++*l;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_time(const char *time)
-{
-	/* convert a time YYHM to wireformat */
-	uint16_t *r = NULL;
-	struct tm tm;
-
-	/* Try to scan the time... */
-	if (!strptime(time, "%Y%m%d%H%M%S", &tm)) {
-		zc_error_prev_line("date and time is expected");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		uint32_t l = htonl(mktime_from_utc(&tm));
-		r = alloc_rdata_init(&l, sizeof(l));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_services(const char *protostr, char *servicestr)
-{
-	/*
-	 * Convert a protocol and a list of service port numbers
-	 * (separated by spaces) in the rdata to wireformat
-	 */
-	uint16_t *r = NULL;
-	uint8_t *p;
-	uint8_t bitmap[65536/8];
-	char sep[] = " ";
-	char *word;
-	int max_port = -8;
-	/* convert a protocol in the rdata to wireformat */
-	struct protoent *proto;
-
-	memset(bitmap, 0, sizeof(bitmap));
-
-	proto = getprotobyname(protostr);
-	if (!proto) {
-		proto = getprotobynumber(atoi(protostr));
-	}
-	if (!proto) {
-		zc_error_prev_line("unknown protocol '%s'", protostr);
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-		return NULL;
-	}
-
-	char *sp = 0;
-	while ((word = strtok_r(servicestr, sep, &sp))) {
-		struct servent *service = NULL;
-		int port;
-
-		service = getservbyname(word, proto->p_name);
-		if (service) {
-			/* Note: ntohs not ntohl!  Strange but true.  */
-			port = ntohs((uint16_t) service->s_port);
-//			printf("assigned port %d\n", port);
-		} else {
-//			printf("else\n");
-			char *end;
-			port = strtol(word, &end, 10);
-			if (*end != '\0') {
-				zc_error_prev_line(
-					"unknown service '%s' for"
-					" protocol '%s'",
-					word, protostr);
-				parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-				return NULL;
-			}
-		}
-
-		if (port < 0 || port > 65535) {
-			zc_error_prev_line("bad port number %d", port);
-		} else {
-			set_bit(bitmap, port);
-			if (port > max_port) {
-				max_port = port;
-			}
-		}
-		servicestr = NULL;
-	}
-
-	r = alloc_rdata(sizeof(uint8_t) + max_port / 8 + 1);
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-		return NULL;
-	}
-
-	p = (uint8_t *)(r + 1);
-	*p = proto->p_proto;
-	memcpy(p + 1, bitmap, *r - 1);
-
-	return r;
-}
-
-uint16_t * zparser_conv_serial(const char *serialstr)
-{
-	uint16_t *r = NULL;
-	uint32_t serial;
-	const char *t;
-
-	serial = strtoserial(serialstr, &t);
-	if (*t != '\0') {
-		zc_error_prev_line("serial is expected");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		serial = htonl(serial);
-		r = alloc_rdata_init(&serial, sizeof(serial));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_period(const char *periodstr)
-{
-	/* convert a time period (think TTL's) to wireformat) */
-	uint16_t *r = NULL;
-	uint32_t period;
-	const char *end;
-
-	/* Allocate required space... */
-	period = strtottl(periodstr, &end);
-	if (*end != '\0') {
-		zc_error_prev_line("time period is expected");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		period = htonl(period);
-		r = alloc_rdata_init(&period, sizeof(period));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_short(const char *text)
-{
-	uint16_t *r = NULL;
-	uint16_t value;
-	char *end;
-
-	value = htons((uint16_t) strtol(text, &end, 10));
-	if (*end != '\0') {
-		zc_error_prev_line("integer value is expected");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		r = alloc_rdata_init(&value, sizeof(value));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_byte(const char *text)
-{
-	uint16_t *r = NULL;
-	uint8_t value;
-	char *end;
-
-	value = (uint8_t) strtol(text, &end, 10);
-	if (*end != '\0') {
-		zc_error_prev_line("integer value is expected");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		r = alloc_rdata_init(&value, sizeof(value));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_algorithm(const char *text)
-{
-	const knot_lookup_table_t *alg;
-	uint8_t id;
-
-	alg = knot_lookup_by_name(dns_algorithms, text);
-	if (alg) {
-		id = (uint8_t) alg->id;
-	} else {
-		char *end;
-		id = (uint8_t) strtol(text, &end, 10);
-		if (*end != '\0') {
-			zc_error_prev_line("algorithm is expected");
-			parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-			return NULL;
-		}
-	}
-
-	uint16_t *r = alloc_rdata_init(&id, sizeof(id));
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-		return NULL;
-	}
-
-	return r;
-}
-
-uint16_t * zparser_conv_certificate_type(const char *text)
-{
-	/* convert a algoritm string to integer */
-	const knot_lookup_table_t *type;
-	uint16_t id;
-
-	type = knot_lookup_by_name(dns_certificate_types, text);
-	if (type) {
-		id = htons((uint16_t) type->id);
-	} else {
-		char *end;
-		id = htons((uint16_t) strtol(text, &end, 10));
-		if (*end != '\0') {
-			zc_error_prev_line("certificate type is expected");
-			parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-			return NULL;
-		}
-	}
-
-	uint16_t *r = alloc_rdata_init(&id, sizeof(id));
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-		return NULL;
-	}
-
-	return r;
-}
-
-uint16_t * zparser_conv_a(const char *text)
-{
-	in_addr_t address;
-	uint16_t *r = NULL;
-
-	if (inet_pton(AF_INET, text, &address) != 1) {
-		zc_error_prev_line("invalid IPv4 address '%s'", text);
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		r = alloc_rdata_init(&address, sizeof(address));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-
-	return r;
-}
-
-uint16_t * zparser_conv_aaaa(const char *text)
-{
-	uint8_t address[IP6ADDRLEN];
-	uint16_t *r = NULL;
-
-	if (inet_pton(AF_INET6, text, address) != 1) {
-		zc_error_prev_line("invalid IPv6 address '%s'", text);
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		r = alloc_rdata_init(address, sizeof(address));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_text(const char *text, size_t len)
-{
-	uint16_t *r = NULL;
-
-	dbg_zp("Converting text: %s\n", text);
-
-	if (len > 255) {
-		zc_error_prev_line("text string is longer than 255 characters,"
-			" try splitting it into multiple parts");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		uint8_t *p;
-		r = alloc_rdata(len + 1);
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-		p = (uint8_t *)(r + 1);
-		*p = len;
-		memcpy(p + 1, text, len);
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_dns_name(const uint8_t *name, size_t len)
-{
-	uint16_t *r = NULL;
-	uint8_t *p = NULL;
-	r = alloc_rdata(len);
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-		return NULL;
-	}
-	p = (uint8_t *)(r + 1);
-	memcpy(p, name, len);
-
-	return r;
-}
-
-uint16_t * zparser_conv_b32(const char *b32)
-{
-	uint8_t buffer[B64BUFSIZE];
-	uint16_t *r = NULL;
-	size_t i = B64BUFSIZE - 1;
-
-	if (strcmp(b32, "-") == 0) {
-		r = alloc_rdata_init("", 1);
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-		return r;
-	}
-
-	/*!< \todo BLEEDING EYES! */
-
-	char b32_copy[strlen(b32) + 1];
-
-	for (int i = 0; i < strlen(b32); i++) {
-		b32_copy[i] = toupper(b32[i]);
-	}
-
-	/*!< \todo BLEEDING EYES! */
-	b32_copy[strlen(b32)] = '\0';
-
-	int32_t b32_ret = base32hex_decode((uint8_t *)b32_copy, strlen(b32_copy),
-	                                   buffer + 1, i);
-
-	i = b32_ret;
-
-	if (b32_ret <= 0) {
-		zc_error_prev_line("invalid base32 data");
-		parser->error_occurred = 1;
-	} else {
-		buffer[0] = i; /* store length byte */
-		r = alloc_rdata_init(buffer, i + 1);
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_b64(const char *b64)
-{
-	uint8_t buffer[B64BUFSIZE];
-	uint16_t *r = NULL;
-	int i;
-
-	i = b64_pton(b64, buffer, B64BUFSIZE);
-	if (i == -1) {
-		zc_error_prev_line("invalid base64 data\n");
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		r = alloc_rdata_init(buffer, i);
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_rrtype(const char *text)
-{
-	uint16_t *r = NULL;
-	uint16_t type = knot_rrtype_from_string(text);
-
-	if (type == 0) {
-		zc_error_prev_line("unrecognized RR type '%s'", text);
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-	} else {
-		type = htons(type);
-		r = alloc_rdata_init(&type, sizeof(type));
-		if (r == NULL) {
-			ERR_ALLOC_FAILED;
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-			return NULL;
-		}
-	}
-	return r;
-}
-
-uint16_t * zparser_conv_nxt(uint8_t nxtbits[])
-{
-	/* nxtbits[] consists of 16 bytes with some zero's in it
-	 * copy every byte with zero to r and write the length in
-	 * the first byte
-	 */
-	uint16_t i;
-	uint16_t last = 0;
-
-	for (i = 0; i < 16; i++) {
-		if (nxtbits[i] != 0) {
-			last = i + 1;
-		}
-	}
-
-	uint16_t *r = alloc_rdata_init(nxtbits, last);
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-		return NULL;
-	}
-
-	return r;
-}
-
-
-/* we potentially have 256 windows, each one is numbered. empty ones
- * should be discarded
- */
-uint16_t * zparser_conv_nsec(uint8_t nsecbits[NSEC_WINDOW_COUNT]
-					     [NSEC_WINDOW_BITS_SIZE])
-{
-	/* nsecbits contains up to 64K of bits which represent the
-	 * types available for a name. Walk the bits according to
-	 * nsec++ draft from jakob
-	 */
-	uint16_t *r;
-	uint8_t *ptr;
-	size_t i, j;
-	uint16_t window_count = 0;
-	uint16_t total_size = 0;
-	uint16_t window_max = 0;
-
-	/* The used windows.  */
-	int used[NSEC_WINDOW_COUNT];
-	/* The last byte used in each the window.  */
-	int size[NSEC_WINDOW_COUNT];
-
-	window_max = 1 + (nsec_highest_rcode / 256);
-
-	/* used[i] is the i-th window included in the nsec
-	 * size[used[0]] is the size of window 0
-	 */
-
-	/* walk through the 256 windows */
-	for (i = 0; i < window_max; ++i) {
-		int empty_window = 1;
-		/* check each of the 32 bytes */
-		for (j = 0; j < NSEC_WINDOW_BITS_SIZE; ++j) {
-			if (nsecbits[i][j] != 0) {
-				size[i] = j + 1;
-				empty_window = 0;
-			}
-		}
-		if (!empty_window) {
-			used[window_count] = i;
-			window_count++;
-		}
-	}
-
-	for (i = 0; i < window_count; ++i) {
-		total_size += sizeof(uint16_t) + size[used[i]];
-	}
-
-	r = alloc_rdata(total_size);
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-		return NULL;
-	}
-	ptr = (uint8_t *)(r + 1);
-
-	/* now walk used and copy it */
-	for (i = 0; i < window_count; ++i) {
-		ptr[0] = used[i];
-		ptr[1] = size[used[i]];
-		memcpy(ptr + 2, &nsecbits[used[i]], size[used[i]]);
-		ptr += size[used[i]] + 2;
-	}
-
-	return r;
-}
-
-/* Parse an int terminated in the specified range. */
-static int parse_int(const char *str,
-		     char **end,
-		     int *result,
-		     const char *name,
-		     int min,
-		     int max)
-{
-	long value;
-	value = strtol(str, end, 10);
-	if (value < min || value > max) {
-		zc_error_prev_line("%s must be within the range [%d .. %d]",
-			name,
-			min,
-			max);
-		return 0;
-	} else {
-		*result = (int) value;
-		return 1;
-	}
-}
-
-/* RFC1876 conversion routines */
-static uint32_t poweroften[10] = {1, 10, 100, 1000, 10000, 100000,
-				  1000000, 10000000, 100000000, 1000000000
-				 };
-
-/*
- * Converts ascii size/precision X * 10**Y(cm) to 0xXY.
- * Sets the given pointer to the last used character.
- *
- */
-static uint8_t precsize_aton(char *cp, char **endptr)
-{
-	unsigned int mval = 0, cmval = 0;
-	uint8_t retval = 0;
-	int exponent;
-	int mantissa;
-
-	while (isdigit((int)*cp)) {
-		mval = mval * 10 + hexdigit_to_int(*cp++);
-	}
-
-	if (*cp == '.') {	/* centimeters */
-		cp++;
-		if (isdigit((int)*cp)) {
-			cmval = hexdigit_to_int(*cp++) * 10;
-			if (isdigit((int)*cp)) {
-				cmval += hexdigit_to_int(*cp++);
-			}
-		}
-	}
-
-	if (mval >= poweroften[7]) {
-		/* integer overflow possible for *100 */
-		mantissa = mval / poweroften[7];
-		exponent = 9; /* max */
-	} else {
-		cmval = (mval * 100) + cmval;
-
-		for (exponent = 0; exponent < 9; exponent++)
-			if (cmval < poweroften[exponent+1]) {
-				break;
-			}
-
-		mantissa = cmval / poweroften[exponent];
-	}
-	if (mantissa > 9) {
-		mantissa = 9;
-	}
-
-	retval = (mantissa << 4) | exponent;
-
-	if (*cp == 'm') {
-		cp++;
-	}
-
-	*endptr = cp;
-
-	return (retval);
-}
-
-/*
- * Parses a specific part of rdata.
- *
- * Returns:
- *
- *	number of elements parsed
- *	zero on error
- *
- */
-uint16_t * zparser_conv_loc(char *str)
-{
-	uint16_t *r;
-	uint32_t *p;
-	int i;
-	int deg, min, secs;	/* Secs is stored times 1000.  */
-	uint32_t lat = 0, lon = 0, alt = 0;
-	/* encoded defaults: version=0 sz=1m hp=10000m vp=10m */
-	uint8_t vszhpvp[4] = {0, 0x12, 0x16, 0x13};
-	char *start;
-	double d;
-
-	for (;;) {
-		deg = min = secs = 0;
-
-		/* Degrees */
-		if (*str == '\0') {
-			zc_error_prev_line("unexpected end of LOC data");
-			return NULL;
-		}
-
-		if (!parse_int(str, &str, &deg, "degrees", 0, 180)) {
-			return NULL;
-		}
-		if (!isspace((int)*str)) {
-			zc_error_prev_line("space expected after degrees");
-			return NULL;
-		}
-		++str;
-
-		/* Minutes? */
-		if (isdigit((int)*str)) {
-			if (!parse_int(str, &str, &min, "minutes", 0, 60)) {
-				return NULL;
-			}
-			if (!isspace((int)*str)) {
-				zc_error_prev_line("space expected after minutes");
-				return NULL;
-			}
-			++str;
-		}
-
-		/* Seconds? */
-		if (isdigit((int)*str)) {
-			start = str;
-			if (!parse_int(str, &str, &i, "seconds", 0, 60)) {
-				return NULL;
-			}
-
-			if (*str == '.' && !parse_int(str + 1, &str, &i,
-						      "seconds fraction",
-						      0, 999)) {
-				return NULL;
-			}
-
-			if (!isspace((int)*str)) {
-				zc_error_prev_line("space expected after seconds");
-				return NULL;
-			}
-			
-			d = strtod(start, &start);
-			if (errno != 0) {
-				zc_error_prev_line("error parsing seconds");
-			}
-
-			if (d < 0.0 || d > 60.0) {
-				zc_error_prev_line(
-					"seconds not in range 0.0 .. 60.0");
-			}
-
-			secs = (int)(d * 1000.0 + 0.5);
-			++str;
-		}
-
-		switch (*str) {
-		case 'N':
-		case 'n':
-			lat = ((uint32_t)1 << 31) +
-				(deg * 3600000 + min * 60000 + secs);
-			break;
-		case 'E':
-		case 'e':
-			lon = ((uint32_t)1 << 31) +
-				(deg * 3600000 + min * 60000 + secs);
-			break;
-		case 'S':
-		case 's':
-			lat = ((uint32_t)1 << 31) -
-				(deg * 3600000 + min * 60000 + secs);
-			break;
-		case 'W':
-		case 'w':
-			lon = ((uint32_t)1 << 31) -
-				(deg * 3600000 + min * 60000 + secs);
-			break;
-		default:
-			zc_error_prev_line(
-				"invalid latitude/longtitude: '%c'", *str);
-			return NULL;
-		}
-		++str;
-
-		if (lat != 0 && lon != 0) {
-			break;
-		}
-
-		if (!isspace((int)*str)) {
-			zc_error_prev_line("space expected after"
-				" latitude/longitude");
-			return NULL;
-		}
-		++str;
-	}
-
-	/* Altitude */
-	if (*str == '\0') {
-		zc_error_prev_line("unexpected end of LOC data");
-		return NULL;
-	}
-
-	if (!isspace((int)*str)) {
-		zc_error_prev_line("space expected before altitude");
-		return NULL;
-	}
-	++str;
-
-	start = str;
-
-	/* Sign */
-	if (*str == '+' || *str == '-') {
-		++str;
-	}
-
-	/* Meters of altitude... */
-	int ret = strtol(str, &str, 10);
-	UNUSED(ret); // Result checked in following switch
-
-	switch (*str) {
-	case ' ':
-	case '\0':
-	case 'm':
-		break;
-	case '.':
-		if (!parse_int(str + 1, &str, &i, "altitude fraction", 0, 99)) {
-			return NULL;
-		}
-		if (!isspace((int)*str) && *str != '\0' && *str != 'm') {
-			zc_error_prev_line("altitude fraction must be a number");
-			return NULL;
-		}
-		break;
-	default:
-		zc_error_prev_line("altitude must be expressed in meters");
-		return NULL;
-	}
-	if (!isspace((int)*str) && *str != '\0') {
-		++str;
-	}
-	
-	d = strtod(start, &start);
-	if (errno != 0) {
-		zc_error_prev_line("error parsing altitued");
-	}
-
-	alt = (uint32_t)(10000000.0 + d * 100 + 0.5);
-
-	if (!isspace((int)*str) && *str != '\0') {
-		zc_error_prev_line("unexpected character after altitude");
-		return NULL;
-	}
-
-	/* Now parse size, horizontal precision and vertical precision if any */
-	for (i = 1; isspace((int)*str) && i <= 3; i++) {
-		vszhpvp[i] = precsize_aton(str + 1, &str);
-
-		if (!isspace((int)*str) && *str != '\0') {
-			zc_error_prev_line("invalid size or precision");
-			return NULL;
-		}
-	}
-
-	/* Allocate required space... */
-	r = alloc_rdata(16);
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		return NULL;
-	}
-	p = (uint32_t *)(r + 1);
-
-	memmove(p, vszhpvp, 4);
-	write_uint32(p + 1, lat);
-	write_uint32(p + 2, lon);
-	write_uint32(p + 3, alt);
-
-	return r;
-}
-
-/*
- * Convert an APL RR RDATA element.
- */
-uint16_t * zparser_conv_apl_rdata(char *str)
-{
-	int negated = 0;
-	uint16_t address_family;
-	uint8_t prefix;
-	uint8_t maximum_prefix;
-	uint8_t length;
-	uint8_t address[IP6ADDRLEN];
-	char *colon = strchr(str, ':');
-	char *slash = strchr(str, '/');
-	int af;
-	int rc;
-	uint16_t rdlength;
-	uint16_t *r;
-	uint8_t *t;
-	char *end;
-	long p;
-
-	if (!colon) {
-		zc_error_prev_line("address family separator is missing");
-		return NULL;
-	}
-	if (!slash) {
-		zc_error_prev_line("prefix separator is missing");
-		return NULL;
-	}
-
-	*colon = '\0';
-	*slash = '\0';
-
-	if (*str == '!') {
-		negated = 1;
-		++str;
-	}
-
-	if (strcmp(str, "1") == 0) {
-		address_family = htons(1);
-		af = AF_INET;
-		length = sizeof(in_addr_t);
-		maximum_prefix = length * 8;
-	} else if (strcmp(str, "2") == 0) {
-		address_family = htons(2);
-		af = AF_INET6;
-		length = IP6ADDRLEN;
-		maximum_prefix = length * 8;
-	} else {
-		zc_error_prev_line("invalid address family '%s'", str);
-		return NULL;
-	}
-
-	rc = inet_pton(af, colon + 1, address);
-	if (rc == 0) {
-		zc_error_prev_line("invalid address '%s'", colon + 1);
-		return NULL;
-	} else if (rc == -1) {
-		char ebuf[256] = {0};
-		strerror_r(errno, ebuf, sizeof(ebuf));
-		zc_error_prev_line("inet_pton failed: %s", ebuf);
-		return NULL;
-	}
-
-	/* Strip trailing zero octets.	*/
-	while (length > 0 && address[length - 1] == 0) {
-		--length;
-	}
-
-
-	p = strtol(slash + 1, &end, 10);
-	if (p < 0 || p > maximum_prefix) {
-		zc_error_prev_line("prefix not in the range 0 .. %d",
-			maximum_prefix);
-		return NULL;
-	} else if (*end != '\0') {
-		zc_error_prev_line("invalid prefix '%s'", slash + 1);
-		return NULL;
-	}
-	prefix = (uint8_t) p;
-
-	rdlength = (sizeof(address_family) + sizeof(prefix) + sizeof(length)
-		    + length);
-	r = alloc_rdata(rdlength);
-	if (r == NULL) {
-		ERR_ALLOC_FAILED;
-		return NULL;
-	}
-	t = (uint8_t *)(r + 1);
-
-	memcpy(t, &address_family, sizeof(address_family));
-	t += sizeof(address_family);
-	memcpy(t, &prefix, sizeof(prefix));
-	t += sizeof(prefix);
-	memcpy(t, &length, sizeof(length));
-	if (negated) {
-		*t |= APL_NEGATION_MASK;
-	}
-	t += sizeof(length);
-	memcpy(t, address, length);
-
-	return r;
-}
-
-/*
- * Below some function that also convert but not to wireformat
- * but to "normal" (int,long,char) types
- */
-
-uint32_t zparser_ttl2int(const char *ttlstr, int *error)
-{
-	/* convert a ttl value to a integer
-	 * return the ttl in a int
-	 * -1 on error
-	 */
-
-	uint32_t ttl;
-	const char *t;
-
-	ttl = strtottl(ttlstr, &t);
-	if (*t != 0) {
-		zc_error_prev_line("invalid TTL value: %s", ttlstr);
-		*error = 1;
-	}
-
-	return ttl;
-}
-
-void zadd_rdata_wireformat(uint16_t *data)
-{
-	parser->temporary_items[parser->rdata_count].raw_data = data;
-	parser->rdata_count++;
-}
-
-/**
- * Used for TXT RR's to grow with undefined number of strings.
- */
-void zadd_rdata_txt_wireformat(uint16_t *data, int first)
-{
-	if (data == NULL) {
-		parser->error_occurred = KNOTDZCOMPILE_EBRDATA;
-		return;
-	}
-	dbg_zp("Adding text!\n");
-	knot_rdata_item_t *rd;
-
-	/* First STR in str_seq, allocate 65K in first unused rdata
-	 * else find last used rdata */
-	if (first) {
-		rd = &parser->temporary_items[parser->rdata_count];
-		rd->raw_data = alloc_rdata(65535 * sizeof(uint8_t));
-		if (rd->raw_data == NULL) {
-			parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-		}
-		parser->rdata_count++;
-		rd->raw_data[0] = 0;
-	} else {
-		rd = &parser->temporary_items[parser->rdata_count-1];
-	}
-
-	if (rd == NULL || rd->raw_data == NULL) {
-		return;
-	}
-
-	if ((size_t)rd->raw_data[0] + (size_t)data[0] > 65535) {
-		zc_error_prev_line("too large rdata element");
-		return;
-	}
-
-	memcpy((uint8_t *)rd->raw_data + 2 + rd->raw_data[0],
-	       data + 1, data[0]);
-	rd->raw_data[0] += data[0];
-	free(data);
-	dbg_zp("Item after add\n");
-//	hex_print(rd->raw_data + 1, rd->raw_data[0]);
-}
-
-void zadd_rdata_domain(knot_dname_t *dname)
-{
-	knot_dname_retain(dname);
-//	printf("Adding rdata name: %s %p\n", dname->name, dname);
-	parser->temporary_items[parser->rdata_count].dname = dname;
-	parser->rdata_count++;
-}
-
-void parse_unknown_rdata(uint16_t type, uint16_t *wireformat)
-{
-	dbg_rdata("parsing unknown rdata for type: %u\n", type);
-	uint16_t size;
-	ssize_t rdata_count;
-	ssize_t i;
-	knot_rdata_item_t *items = NULL;
-
-	if (wireformat) {
-		size = *wireformat;
-	} else {
-		return;
-	}
-
-	rdata_count = rdata_wireformat_to_rdata_atoms(wireformat + 1, type,
-						      size, &items);
-	dbg_rdata("got %d items\n", rdata_count);
-	if (rdata_count < 0) {
-		dbg_rdata("wf to items returned error: %s (%d)\n",
-		          error_to_str(knot_zcompile_error_msgs, rdata_count),
-		          rdata_count);
-		zc_error_prev_line("bad unknown RDATA\n");
-		/*!< \todo leaks */
-		return;
-	}
-
-	for (i = 0; i < rdata_count; ++i) {
-		if (rdata_atom_is_domain(type, i)) {
-			zadd_rdata_domain(items[i].dname);
-		} else {
-			//XXX won't this create size two times?
-			zadd_rdata_wireformat((uint16_t *)items[i].raw_data);
-		}
-	}
-	free(items);
-	/* Free wireformat */
-	free(wireformat);
-	
-	dbg_rdata("parse_unknown_rdata: Successfuly parsed unknown rdata.\n");
-}
-
-void set_bitnsec(uint8_t bits[NSEC_WINDOW_COUNT][NSEC_WINDOW_BITS_SIZE],
-	                uint16_t index)
-{
-	/*
-	 * The bits are counted from left to right, so bit #0 is the
-	 * left most bit.
-	 */
-	uint8_t window = index / 256;
-	uint8_t bit = index % 256;
-
-	bits[window][bit / 8] |= (1 << (7 - bit % 8));
-}
-
-/*! @} */
diff --git a/src/zcompile/parser-util.h b/src/zcompile/parser-util.h
deleted file mode 100644
index 57258dc52bc385f8e3bbd4ea3799597107b33e04..0000000000000000000000000000000000000000
--- a/src/zcompile/parser-util.h
+++ /dev/null
@@ -1,357 +0,0 @@
-/*!
- * \file parser-util.h
- *
- * \author NLnet Labs
- *         Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *         Minor modifications by CZ.NIC, z.s.p.o.
- *
- * \brief Zone compiler utility functions.
- *
- * \addtogroup zoneparser
- * @{
- */
-
-/*
- * Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * This software is open source.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- *
- * Neither the name of the NLNET LABS nor the names of its contributors may
- * be used to endorse or promote products derived from this software without
- * specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef _KNOTD_PARSER_UTIL_H_
-#define _KNOTD_PARSER_UTIL_H_
-
-#include <assert.h>
-#include <fcntl.h>
-#include <ctype.h>
-#include <errno.h>
-#include <limits.h>
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-#include <stdlib.h>
-#include <time.h>
-#include <netinet/in.h>
-#include <netdb.h>
-
-#include "zcompile/zcompile.h"
-#include "libknot/util/descriptor.h"
-
-int inet_pton4(const char *src, uint8_t *dst);
-int inet_pton6(const char *src, uint8_t *dst);
-//int my_b32_pton(const char *src, uint8_t *target, size_t tsize);
-const char *inet_ntop4(const u_char *src, char *dst, size_t size);
-const char *inet_ntop6(const u_char *src, char *dst, size_t size);
-int inet_pton(int af, const char *src, void *dst);
-void b64_initialize_rmap();
-int b64_pton_do(char const *src, uint8_t *target, size_t targsize);
-int b64_pton_len(char const *src);
-int b64_pton(char const *src, uint8_t *target, size_t targsize);
-void set_bit(uint8_t bits[], size_t index);
-uint32_t strtoserial(const char *nptr, const char **endptr);
-void write_uint32(void *dst, uint32_t data);
-uint32_t strtottl(const char *nptr, const char **endptr);
-time_t mktime_from_utc(const struct tm *tm);
-
-/*!< Conversions from text to wire. */
-/*!
- * \brief Converts hex text format to wireformat.
- *
- * \param hex String to be converted.
- * \param len Length of string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_hex(const char *hex, size_t len);
-
-/*!
- * \brief Converts hex text format with length to wireformat.
- *
- * \param hex String to be converted/.
- * \param len Length of string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_hex_length(const char *hex, size_t len);
-
-/*!
- * \brief Converts time string to wireformat.
- *
- * \param time Time string to be converted.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_time(const char *time);
-/*!
- * \brief Converts a protocol and a list of service port numbers
- * (separated by spaces) in the rdata to wireformat
- *
- * \param protostr Protocol string.
- * \param servicestr Service string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_services(const char *protostr, char *servicestr);
-
-/*!
- * \brief Converts serial to wireformat.
- *
- * \param serialstr Serial string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_serial(const char *serialstr);
-/*!
- * \brief Converts period to wireformat.
- *
- * \param periodstr Period string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_period(const char *periodstr);
-
-/*!
- * \brief Converts short int to wireformat.
- *
- * \param text String containing short int.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_short(const char *text);
-
-/*!
- * \brief Converts long int to wireformat.
- *
- * \param text String containing long int.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_long(const char *text);
-
-/*!
- * \brief Converts byte to wireformat.
- *
- * \param text String containing byte.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_byte(const char *text);
-
-/*!
- * \brief Converts A rdata string to wireformat.
- *
- * \param text String containing A rdata.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_a(const char *text);
-
-/*!
- * \brief Converts AAAA rdata string to wireformat.
- *
- * \param text String containing AAAA rdata.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_aaaa(const char *text);
-
-/*!
- * \brief Converts text string to wireformat.
- *
- * \param text Text string.
- * \param len Length of string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_text(const char *text, size_t len);
-
-/*!
- * \brief Converts domain name string to wireformat.
- *
- * \param name Domain name string.
- * \param len Length of string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_dns_name(const uint8_t* name, size_t len);
-
-/*!
- * \brief Converts base32 encoded string to wireformat.
- * TODO consider replacing with our implementation.
- *
- * \param b32 Base32 encoded string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_b32(const char *b32);
-
-/*!
- * \brief Converts base64 encoded string to wireformat.
- * TODO consider replacing with our implementation.
- *
- * \param b64 Base64 encoded string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_b64(const char *b64);
-
-/*!
- * \brief Converts RR type string to wireformat.
- *
- * \param rr RR type string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_rrtype(const char *rr);
-
-/*!
- * \brief Converts NXT string to wireformat.
- *
- * \param nxtbits NXT string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_nxt(uint8_t *nxtbits);
-
-/*!
- * \brief Converts NSEC bitmap to wireformat.
- *
- * \param nsecbits[][] NSEC bits.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_nsec(uint8_t nsecbits[NSEC_WINDOW_COUNT]
-					   [NSEC_WINDOW_BITS_SIZE]);
-/*!
- * \brief Converts LOC string to wireformat.
- *
- * \param str LOC string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_loc(char *str);
-
-/*!
- * \brief Converts algorithm string to wireformat.
- *
- * \param algstr Algorithm string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_algorithm(const char *algstr);
-
-/*!
- * \brief Converts certificate type string to wireformat.
- *
- * \param typestr Certificate type mnemonic string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_certificate_type(const char *typestr);
-
-/*!
- * \brief Converts APL data to wireformat.
- *
- * \param str APL data string.
- *
- * \return Converted wireformat.
- */
-uint16_t *zparser_conv_apl_rdata(char *str);
-
-/*!
- * \brief Parses unknown rdata.
- *
- * \param type Type of data.
- * \param wireformat Wireformat of data.
- *
- * \return Converted wireformat.
- */
-void parse_unknown_rdata(uint16_t type, uint16_t *wireformat);
-
-/*!
- * \brief Converts TTL string to int.
- *
- * \param ttlstr String
- * \param error Error code.
- *
- * \return Converted wireformat.
- */
-uint32_t zparser_ttl2int(const char *ttlstr, int* error);
-
-/*!
- * \brief Adds wireformat to temporary list of rdata items.
- *
- * \param data Wireformat to be added.
- */
-void zadd_rdata_wireformat(uint16_t *data);
-
-/*!
- * \brief Adds TXT wireformat to temporary list of rdata items.
- *
- * \param data Wireformat to be added.
- * \param first This is first text to be added.
- */
-void zadd_rdata_txt_wireformat(uint16_t *data, int first);
-
-/*!
- * \brief Cleans after using zadd_rdata_txt_wireformat().
- */
-void zadd_rdata_txt_clean_wireformat();
-
-/*!
- * \brief Adds domain name to temporary list of rdata items.
- *
- * \param domain Domain name to be added.
- */
-void zadd_rdata_domain(knot_dname_t *domain);
-
-/*!
- * \brief Sets bit in NSEC bitmap.
- *
- * \param bits[][] NSEC bitmaps.
- * \param index Index on which bit is to be set.
- */
-void set_bitnsec(uint8_t bits[NSEC_WINDOW_COUNT][NSEC_WINDOW_BITS_SIZE],
-		 uint16_t index);
-
-/*!
- * \brief Allocate and init wireformat.
- *
- * \param data Data to be copied into newly created wireformat.
- * \param size Size of data.
- *
- * \return Allocated wireformat.
- */
-uint16_t *alloc_rdata_init(const void *data, size_t size);
-uint16_t rrsig_type_covered(knot_rrset_t *rrset);
-
-
-#endif /* _KNOTD_PARSER_UTIL_H_ */
-
-/*! @} */
diff --git a/src/zcompile/tests/unittests_zp_main.c b/src/zcompile/tests/unittests_zp_main.c
deleted file mode 100644
index 5d8c5e9166248e6a849e2e86e42f42012d71573c..0000000000000000000000000000000000000000
--- a/src/zcompile/tests/unittests_zp_main.c
+++ /dev/null
@@ -1,62 +0,0 @@
-/*  Copyright (C) 2011 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <config.h>
-#include "knot/common.h"
-#include "common/libtap/tap_unit.h"
-
-// Units to test
-#include "zcompile_tests.c"
-
-// Run all loaded units
-int main(int argc, char *argv[])
-{
-	// Open log
-	//log_init(LOG_UPTO(LOG_ERR), LOG_MASK(LOG_ERR) | LOG_MASK(LOG_WARNING));
-
-	// Build test set
-	unit_api *tests[] = {
-		&zoneparser_tests_api, //! Zoneparser unit
-		NULL
-	};
-
-	// Plan number of tests
-	int id = 0;
-	int test_count = 0;
-	note("Units:");
-	while (tests[id] != NULL) {
-		note("- %s : %d tests", tests[id]->name,
-		     tests[id]->count(argc, argv));
-		test_count += tests[id]->count(argc, argv);
-		++id;
-	}
-
-	plan(test_count);
-
-	// Run tests
-	id = 0;
-	while (tests[id] != NULL) {
-		diag("Testing unit: %s", tests[id]->name);
-		tests[id]->run(argc, argv);
-		++id;
-	}
-
-	//log_close();
-
-	// Evaluate
-	return exit_status();
-}
-
diff --git a/src/zcompile/tests/zcompile_tests.c b/src/zcompile/tests/zcompile_tests.c
deleted file mode 100644
index 5d3dce6e1b4ad23904198742f8a4d781a1427c9c..0000000000000000000000000000000000000000
--- a/src/zcompile/tests/zcompile_tests.c
+++ /dev/null
@@ -1,425 +0,0 @@
-/*  Copyright (C) 2011 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <assert.h>
-
-#include "libknot/zone/zone.h"
-#include "knot/zone/zone-load.h"
-#include "knot/common.h"
-#include "libknot/rrset.h"
-#include "libknot/util/descriptor.h"
-#include "zcompile/zcompile.h"
-
-#ifdef TEST_WITH_LDNS
-#include "ldns/ldns.h"
-#endif
-
-static int zoneparser_tests_count(int argc, char *argv[]);
-static int zoneparser_tests_run(int argc, char *argv[]);
-
-/*
- * Unit API.
- */
-unit_api zoneparser_tests_api = {
-	"Zoneparser",
-	&zoneparser_tests_count,
-	&zoneparser_tests_run
-};
-
-#ifdef TEST_WITH_LDNS
-/*
- *  Unit implementation.
- */static int compare_wires_simple_zp(uint8_t *wire1,
-				      uint8_t *wire2, uint count)
-{
-	int i = 0;
-	while (i < count &&
-	       wire1[i] == wire2[i]) {
-		i++;
-	}
-	return (!(count == i));
-}
-
-/* compares only one rdata */
-static int compare_rr_rdata_silent(knot_rdata_t *rdata, ldns_rr *rr,
-				   uint16_t type)
-{
-	knot_rrtype_descriptor_t *desc =
-		knot_rrtype_descriptor_by_type(type);
-	for (int i = 0; i < rdata->count; i++) {
-		/* TODO check for ldns "descriptors" as well */
-		if (desc->wireformat[i] == KNOT_RDATA_WF_COMPRESSED_DNAME ||
-		    desc->wireformat[i] == KNOT_RDATA_WF_LITERAL_DNAME ||
-		    desc->wireformat[i] == KNOT_RDATA_WF_UNCOMPRESSED_DNAME) {
-			assert(ldns_rr_rdf(rr, i));
-			if (rdata->items[i].dname->size !=
-			    ldns_rdf_size(ldns_rr_rdf(rr, i))) {
-				return 1;
-			}
-			if (compare_wires_simple_zp(rdata->items[i].dname->name,
-				ldns_rdf_data(ldns_rr_rdf(rr, i)),
-				rdata->items[i].dname->size) != 0) {
-				return 1;
-			}
-		} else {
-			if (ldns_rr_rdf(rr, i) == NULL &&
-			    rdata->items[i].raw_data[0] != 0) {
-				return 1;
-			} else {
-				continue;
-			}
-			if (rdata->items[i].raw_data[0] !=
-			    ldns_rdf_size(ldns_rr_rdf(rr, i))) {
-
-				/* ldns stores the size including the
-				 * length, dnslib does not */
-				if (abs(rdata->items[i].raw_data[0] -
-				    ldns_rdf_size(ldns_rr_rdf(rr, i))) != 1) {
-					return 1;
-				}
-			}
-			if (compare_wires_simple_zp((uint8_t *)
-				(rdata->items[i].raw_data + 1),
-				ldns_rdf_data(ldns_rr_rdf(rr, i)),
-				rdata->items[i].raw_data[0]) != 0) {
-				return 1;
-			}
-		}
-	}
-	return 0;
-}
-
-static int compare_rrset_w_ldns_rrset(const knot_rrset_t *rrset,
-				      ldns_rr_list *rrs,
-				      char check_rdata, char verbose)
-{
-	/* We should have only one rrset from ldns, although it is
-	 * represented as rr_list ... */
-
-	/* TODO errors */
-
-	assert(rrs);
-	assert(rrset);
-
-	ldns_rr_list_sort(rrs);
-
-	/* compare headers */
-
-	ldns_rr *rr = ldns_rr_list_rr(rrs, 0);
-
-	if (rrset->owner->size != ldns_rdf_size(ldns_rr_owner(rr))) {
-		diag("RRSet owner names differ in length");
-		if (!verbose) {
-			return 1;
-		}
-		diag("ldns: %d, dnslib: %d", ldns_rdf_size(ldns_rr_owner(rr)),
-		     rrset->owner->size);
-		diag("%s", knot_dname_to_str(rrset->owner));
-		diag("%s", ldns_rdf_data(ldns_rr_owner(rr)));
-		return 1;
-	}
-
-	if (compare_wires_simple_zp(rrset->owner->name,
-				   ldns_rdf_data(ldns_rr_owner(rr)),
-				   rrset->owner->size) != 0) {
-		diag("RRSet owner wireformats differ");
-		return 1;
-	}
-
-	if (rrset->type != ldns_rr_get_type(rr)) {
-		diag("RRset types differ");
-		if (!verbose) {
-			return 1;
-		}
-		diag("Dnslib type: %d Ldns type: %d", rrset->type,
-		     ldns_rr_get_type(rr));
-		return 1;
-	}
-
-	if (rrset->rclass != ldns_rr_get_class(rr)) {
-		diag("RRset classes differ");
-		return 1;
-	}
-
-	if (rrset->ttl != ldns_rr_ttl(rr)) {
-		diag("RRset TTLs differ");
-		if (!verbose) {
-			return 1;
-		}
-		diag("dnslib: %d ldns: %d", rrset->ttl, ldns_rr_ttl(rr));
-		return 1;
-	}
-
-	if (!check_rdata) {
-		return 0;
-	}
-
-	/* compare rdatas */
-
-	/* sort dnslib rdata */
-
-	knot_rdata_t *tmp_rdata = rrset->rdata;
-
-	rr = ldns_rr_list_pop_rr(rrs);
-
-	char found;
-
-	while (rr != NULL) {
-		found = 0;
-		tmp_rdata = rrset->rdata;
-		while (!found &&
-		       tmp_rdata->next != rrset->rdata) {
-			if (compare_rr_rdata_silent(tmp_rdata, rr,
-						    rrset->type) == 0) {
-				found = 1;
-			}
-			tmp_rdata = tmp_rdata->next;
-		}
-
-		if (!found &&
-		    compare_rr_rdata_silent(tmp_rdata, rr, rrset->type) == 0) {
-			found = 1;
-		}
-
-		/* remove the found rdata from list */
-		if (!found) {
-			diag("RRsets rdata differ");
-			return 1;
-		}
-		ldns_rr_free(rr);
-
-		rr = ldns_rr_list_pop_rr(rrs);
-	}
-
-	return 0;
-}
-
-int compare_zones(knot_zone_contents_t *zone,
-                  ldns_rr_list *ldns_list, char verbose)
-{
-	/* TODO currently test fail when encountering first error -
-	 * it should finish going through the zone */
-	knot_rrset_t *tmp_rrset = NULL;
-
-	knot_dname_t *tmp_dname = NULL;
-
-	knot_node_t *node = NULL;
-
-	ldns_rr_list *ldns_rrset = ldns_rr_list_pop_rrset(ldns_list);
-
-	if (ldns_rrset == NULL) {
-		diag("Error: empty node");
-		return 1;
-	}
-
-	ldns_rr *rr = NULL;
-
-	/*
-	 * Following cycle works like this: First, we get RR from ldns rrset,
-	 * then we search for the node containing the rrset, then we get the
-	 * rrset, which is then compared with whole ldns rrset.
-	 */
-
-	/* ldns_rr_list_pop_rrset should pop the first rrset */
-	while (ldns_rrset != NULL) {
-		rr = ldns_rr_list_rr(ldns_rrset, 0);
-		tmp_dname =
-		knot_dname_new_from_wire(ldns_rdf_data(ldns_rr_owner(rr)),
-					   ldns_rdf_size(ldns_rr_owner(rr)),
-					   NULL);
-
-		node = knot_zone_contents_get_node(zone, tmp_dname);
-
-		if (node == NULL) {
-			node = knot_zone_contents_get_nsec3_node(zone,
-			                                         tmp_dname);
-		}
-
-		if (node == NULL) {
-			diag("Could not find node");
-			diag("%s", knot_dname_to_str(tmp_dname));
-			return 1;
-		}
-
-		knot_dname_free(&tmp_dname);
-
-		tmp_rrset = knot_node_get_rrset(node,
-				ldns_rr_get_type(ldns_rr_list_rr(ldns_rrset,
-								 0)));
-
-		if (tmp_rrset == NULL &&
-		    (uint)(ldns_rr_get_type(ldns_rr_list_rr(ldns_rrset, 0))) !=
-		    (uint)KNOT_RRTYPE_RRSIG) {
-			diag("Could not find rrset");
-			if (!verbose) {
-				return 1;
-			}
-			ldns_rr_list_print(stdout, ldns_rrset);
-			diag("%s", knot_dname_to_str(node->owner));
-			return 1;
-		} else if ((uint)(ldns_rr_get_type(ldns_rr_list_rr(ldns_rrset,
-		                                                  0))) ==
-			   (uint)KNOT_RRTYPE_RRSIG) {
-			knot_rrset_t *rrsigs = NULL;
-			/* read type covered from ldns rrset */
-			for (int i = 0; i < ldns_rrset->_rr_count; i++) {
-				uint16_t type_covered =
-				ldns_rdf_data(ldns_rr_rdf(
-					ldns_rr_list_rr(ldns_rrset, i), 0))[1];
-
-				/*
-				 * Dnslib stores RRSIGs separately -
-				 * we have to find get it from its "parent"
-				 * rrset.
-				 */
-
-				tmp_rrset = knot_node_get_rrset(node,
-								  type_covered);
-
-				if (tmp_rrset == NULL) {
-					if (!verbose) {
-						return 1;
-					}
-					diag("following rrset "
-					     "could not be found");
-					ldns_rr_list_print(stdout, ldns_rrset);
-					return 1;
-				}
-
-				if (rrsigs == NULL) {
-					rrsigs = tmp_rrset->rrsigs;
-				} else {
-					knot_rrset_merge((void *)&rrsigs,
-					(void *)&(tmp_rrset->rrsigs));
-				}
-			}
-			tmp_rrset = rrsigs;
-		}
-
-/*		diag("dnslib type: %d", tmp_rrset->type);
-		diag("dnslib dname: %s", tmp_rrset->owner->name);
-
-		diag("ldns type: %d",
-		     ldns_rr_get_type(ldns_rr_list_rr(ldns_rrset, 0)));
-		diag("ldns dname : %s", ldns_rdf_data(ldns_rr_owner(
-				ldns_rr_list_rr(ldns_rrset, 0)))); */
-
-//		knot_rrset_dump(tmp_rrset, 1);
-
-		if (compare_rrset_w_ldns_rrset(tmp_rrset, ldns_rrset,
-					       1, 0) != 0) {
-			diag("RRSets did not match");
-//			knot_rrset_dump(tmp_rrset, 1);
-			return 1;
-		}
-
-		ldns_rr_list_deep_free(ldns_rrset);
-
-		ldns_rrset = ldns_rr_list_pop_rrset(ldns_list);
-
-		if (ldns_rrset == NULL) {
-			ldns_rrset = ldns_rr_list_pop_rrset(ldns_list);
-		}
-	}
-
-	return 0;
-}
-
-#endif
-
-static int test_zoneparser_zone_read(const char *origin, const char *filename,
-				     const char *outfile)
-{
-#ifndef TEST_WITH_LDNS
-	diag("Zoneparser tests without usage of ldns are not implemented");
-	return 0;
-#endif
-
-#ifdef TEST_WITH_LDNS
-	/* Calls zcompile. */
-	parser = zparser_create();
-	int ret = zone_read(origin, filename, outfile, 0);
-	if (ret != 0) {
-		diag("Could not load zone from file: %s", filename);
-		return 0;
-	}
-
-	knot_zone_t *dnsl_zone = NULL;
-	zloader_t *loader = NULL;
-	if (knot_zload_open(&loader, outfile) != 0) {
-		diag("Could not create zone loader.\n");
-		return 0;
-	}
-	dnsl_zone = knot_zload_load(loader);
-	remove(outfile);
-	if (!dnsl_zone) {
-		diag("Could not load dumped zone.\n");
-		return 0;
-	}
-
-	ldns_zone *ldns_zone = NULL;
-	FILE *f = fopen(filename, "r");
-	if (ldns_zone_new_frm_fp(&ldns_zone, f, NULL,
-				  0, LDNS_RR_CLASS_IN) != LDNS_STATUS_OK) {
-		diag("Could not load zone from file: %s (ldns)", filename);
-		return 0;
-	}
-
-//	ldns_zone_sort(ldns_zone);
-
-	/*
-	 * LDNS stores SOA record independently - create a list with all
-	 * records in it.
-	 */
-
-	ldns_rr_list *ldns_list = ldns_zone_rrs(ldns_zone);
-
-	ldns_rr_list_push_rr(ldns_list, ldns_zone_soa(ldns_zone));
-
-	if (compare_zones(dnsl_zone->contents, ldns_list, 0) != 0) {
-		return 0;
-	}
-
-	knot_zone_deep_free(&dnsl_zone, 0);
-	ldns_zone_free(ldns_zone);
-	fclose(f);
-	return 1;
-#endif
-}
-
-static const int ZONEPARSER_TEST_COUNT = 1;
-
-/*! API: return number of tests. */
-static int zoneparser_tests_count(int argc, char *argv[])
-{
-	return ZONEPARSER_TEST_COUNT;
-}
-
-/*! API: run tests. */
-static int zoneparser_tests_run(int argc, char *argv[])
-{
-	if (argc == 3) {
-		ok(test_zoneparser_zone_read(argv[1], argv[2],
-					     "foo_test_zone"),
-					     "zoneparser: read (%s)",
-		   argv[2]);
-	} else {
-		diag("Wrong parameters\n usage: "
-		     "knot-zcompile-unittests origin zonefile");
-		return 0;
-	}
-	return 1;
-}
diff --git a/src/zcompile/zcompile-error.h b/src/zcompile/zcompile-error.h
deleted file mode 100644
index c6d999c2aec7c193eb50ac3f762dfa882bf88f70..0000000000000000000000000000000000000000
--- a/src/zcompile/zcompile-error.h
+++ /dev/null
@@ -1,90 +0,0 @@
-/*!
- * \file zcompile-error.h
- *
- * \author Lubos Slovak <lubos.slovak@nic.cz>
- * \author Marek Vavrusa <marek.vavrusa@nic.cz>
- * \author Jan Kadlec <jan.kadlec@nic.cz>
- *
- * \brief Error codes and function for getting error message.
- *
- * \addtogroup zoneparser
- * @{
- */
-/*  Copyright (C) 2011 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
- */
-
-#ifndef _KNOTD_ZCOMPILE_ERROR_H_
-#define _KNOTD_ZCOMPILE_ERROR_H_
-
-#include "common/errors.h"
-
-/*!
- * \brief Error codes used in the server.
- *
- * Some viable errors are directly mapped
- * to libc errno codes.
- */
-enum knot_zcompile_error {
-
-	/* Directly mapped error codes. */
-	KNOTDZCOMPILE_EOK = 0,
-	KNOTDZCOMPILE_ENOMEM = -ENOMEM, /*!< \brief Out of memory. */
-	KNOTDZCOMPILE_EINVAL = -EINVAL, /*!< \brief Invalid parameter passed. */
-	/*!
-	 * \brief Parameter not supported.
-	 */
-	KNOTDZCOMPILE_ENOTSUP = -ENOTSUP,
-	KNOTDZCOMPILE_EBUSY = -EBUSY, /*!< \brief Requested resource is busy. */
-	/*!
-	 * \brief OS lacked necessary resources.
-	 */
-	KNOTDZCOMPILE_EAGAIN = -EAGAIN,
-	KNOTDZCOMPILE_EACCES = -EACCES, /*!< \brief Permission is denied. */
-	/*!
-	 * \brief Connection is refused.
-	 */
-	KNOTDZCOMPILE_ECONNREFUSED = -ECONNREFUSED,
-	KNOTDZCOMPILE_EISCONN = -EISCONN, /*!< \brief Already connected. */
-	/*!
-	 * \brief Address already in use.
-	 */
-	KNOTDZCOMPILE_EADDRINUSE = -EADDRINUSE,
-	KNOTDZCOMPILE_ENOENT = -ENOENT, /*!< \brief Resource not found. */
-	KNOTDZCOMPILE_ERANGE = -ERANGE, /*!< \brief Value is out of range. */
-
-	/* Custom error codes. */
-	KNOTDZCOMPILE_ERROR = -16384, /*!< \brief Generic error. */
-	KNOTDZCOMPILE_ESYNT, /*!< \brief Syntax error. */
-	KNOTDZCOMPILE_EBADNODE, /*!< \brief Node error. */
-	KNOTDZCOMPILE_EBRDATA, /*!< \brief RDATA error. */
-	KNOTDZCOMPILE_EBADSOA, /*!< \brief SOA owner error. */
-	KNOTDZCOMPILE_ESOA, /*!< \brief Multiple SOA records. */
-
-	KNOTDZCOMPILE_EZONEINVAL, /*!< \brief Invalid zone file. */
-	KNOTDZCOMPILE_EPARSEFAIL, /*!< \brief Parser fail. */
-	KNOTDZCOMPILE_ENOIPV6, /*! \brief No IPv6 support. */
-
-	KNOTDZCOMPILE_ERROR_COUNT = 22
-};
-
-typedef enum knot_zcompile_error knot_zcompile_error_t;
-
-/*! \brief Table linking error messages to error codes. */
-extern const error_table_t knot_zcompile_error_msgs[KNOTDZCOMPILE_ERROR_COUNT];
-
-#endif /* _KNOTD_ZCOMPILE_ERROR_H_ */
-
-/*! @} */
diff --git a/src/zcompile/zcompile.c b/src/zcompile/zcompile.c
deleted file mode 100644
index afc036a749f0ec7a3313840838763547df3001e0..0000000000000000000000000000000000000000
--- a/src/zcompile/zcompile.c
+++ /dev/null
@@ -1,673 +0,0 @@
-/*!
- * \file zcompile.c
- *
- * \author Jan Kadlec <jan.kadlec@nic.cz>. Minor portions of code taken from
- *         NSD.
- *
- * \brief Zone compiler.
- *
- * \addtogroup zoneparser
- * @{
- */
-
-/*  Copyright (C) 2011 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <config.h>
-#include <assert.h>
-#include <ctype.h>
-#include <stdio.h>
-#include <string.h>
-#include <stdlib.h>
-#include <assert.h>
-#include <sys/stat.h>
-
-#include "common/base32hex.h"
-#include "common/log.h"
-#include "knot/other/debug.h"
-#include "zcompile/zcompile.h"
-#include "zcompile/parser-util.h"
-#include "zcompile/zcompile-error.h"
-#include "knot/zone/zone-dump.h"
-#include "libknot/zone/zone-diff.h"
-#include "libknot/rrset.h"
-#include "libknot/util/utils.h"
-#include "zscanner/file_loader.h"
-
-//#define dbg_zp_detail printf
-//#define dbg_zp printf
-
-//#define dbg_zp_exec_detail(cmds) do { cmds } while (0)
-
-static long rr_count = 0;
-static long new_rr_count = 0;
-static long new_dname_count = 0;
-static long err_count = 0;
-
-struct parser_context {
-	rrset_list_t *node_rrsigs;
-	knot_zone_contents_t *current_zone;
-	knot_rrset_t *current_rrset;
-	knot_dname_t *origin_from_config;
-	knot_node_t *last_node;
-	int ret;
-};
-
-typedef struct parser_context parser_context_t;
-
-/*!
- * \brief Adds RRSet to list.
- *
- * \param head Head of list.
- * \param rrsig RRSet to be added.
- */
-static int rrset_list_add(rrset_list_t **head, knot_rrset_t *rrsig)
-{
-	if (*head == NULL) {
-		*head = malloc(sizeof(rrset_list_t));
-		if (*head == NULL) {
-			ERR_ALLOC_FAILED;
-			return KNOTDZCOMPILE_ENOMEM;
-		}
-		(*head)->next = NULL;
-		(*head)->data = rrsig;
-	} else {
-		rrset_list_t *tmp = malloc(sizeof(*tmp));
-		if (tmp == NULL) {
-			ERR_ALLOC_FAILED;
-			return KNOTDZCOMPILE_ENOMEM;
-		}
-		tmp->next = *head;
-		tmp->data = rrsig;
-		*head = tmp;
-	}
-	
-	dbg_zp_verb("zp: rrset_add: Added RRSIG %p to list.\n", rrsig);
-
-	return KNOTDZCOMPILE_EOK;
-}
-
-/*!
- * \brief Deletes RRSet list. Sets pointer to NULL.
- *
- * \param head Head of list to be deleted.
- */
-static void rrset_list_delete(rrset_list_t **head)
-{
-	rrset_list_t *tmp;
-	if (*head == NULL) {
-		return;
-	}
-
-	while (*head != NULL) {
-		tmp = *head;
-		*head = (*head)->next;
-		free(tmp);
-	}
-
-	*head = NULL;
-	
-	dbg_zp("zp: list_delete: List deleleted.\n");
-}
-
-static int find_rrset_for_rrsig_in_node(knot_zone_contents_t *zone,
-                                 knot_node_t *node,
-                                 knot_rrset_t *rrsig)
-{
-	assert(node);
-
-	assert(knot_dname_compare(rrsig->owner, node->owner) == 0);
-
-	knot_rrset_t *tmp_rrset =
-		knot_node_get_rrset(node,
-	                            knot_rrset_rdata_rrsig_type_covered(rrsig));
-
-	int ret;
-
-	if (tmp_rrset == NULL) {
-		dbg_zp("zp: find_rr_for_sig_in_node: Node does not contain "
-		       "RRSet of type %d.\n",
-		       knot_rrset_rdata_rrsig_type_covered(rrsig));
-		tmp_rrset = knot_rrset_new(rrsig->owner,
-		                           knot_rrset_rdata_rrsig_type_covered(rrsig),
-		                           rrsig->rclass,
-		                           rrsig->ttl);
-		if (tmp_rrset == NULL) {
-			dbg_zp("zp: find_rr_for_sig_in_node: Cannot create "
-			       "dummy RRSet.\n");
-			return KNOT_ERROR;
-		}
-
-		ret = knot_zone_contents_add_rrset(zone, tmp_rrset, &node,
-		                                   KNOT_RRSET_DUPL_MERGE, 1);
-		assert(ret <= 0);
-		if (ret < 0) {
-			dbg_zp("zp: Failed to add new dummy RRSet to the zone."
-			       "\n");
-			return KNOT_ERROR;
-		}
-	}
-	
-	assert(tmp_rrset);
-	
-	if (tmp_rrset->ttl != rrsig->ttl) {
-		char *name = knot_dname_to_str(tmp_rrset->owner);
-		assert(name);
-		log_zone_warning("RRSIG owned by: %s cannot be added to "
-		                 "its RRSet, because their TTLs differ. "
-		                 "Changing TTL to value=%d.\n",
-		                 name, tmp_rrset->ttl);
-		free(name);
-	}
-
-	ret = knot_zone_contents_add_rrsigs(zone, rrsig, &tmp_rrset, &node,
-			                    KNOT_RRSET_DUPL_MERGE, 1);
-	if (ret < 0) {
-		dbg_zp("zp: find_rr_for_sig: Cannot add RRSIG.\n");
-		return KNOTDZCOMPILE_EINVAL;
-	} else if (ret > 0) {
-		knot_rrset_deep_free(&rrsig, 0, 0);
-	}
-	
-	knot_dname_release(tmp_rrset->owner);
-
-	assert(tmp_rrset->rrsigs != NULL);
-
-	return KNOTDZCOMPILE_EOK;
-}
-
-static knot_node_t *create_node(knot_zone_contents_t *zone,
-	knot_rrset_t *current_rrset,
-	int (*node_add_func)(knot_zone_contents_t *zone, knot_node_t *node,
-	                     int create_parents, uint8_t, int),
-	knot_node_t *(*node_get_func)(const knot_zone_contents_t *zone,
-					const knot_dname_t *owner))
-{
-	dbg_zp_verb("zp: create_node: Creating node using RRSet: %p.\n",
-	            current_rrset);
-	knot_node_t *node =
-		knot_node_new(current_rrset->owner, NULL, 0);
-	if (node_add_func(zone, node, 1, 0, 1) != 0) {
-		return NULL;
-	}
-	
-	assert(current_rrset->owner == node->owner);
-
-	return node;
-}
-
-static void process_rrsigs_in_node(parser_context_t *parser,
-                                   knot_zone_contents_t *zone,
-                                   knot_node_t *node)
-{
-	dbg_zp_verb("zp: process_rrsigs: Processing RRSIGS in node: %p.\n",
-	            node);
-	rrset_list_t *tmp = parser->node_rrsigs;
-	while (tmp != NULL) {
-		if (find_rrset_for_rrsig_in_node(zone, node,
-						 tmp->data) != KNOT_EOK) {
-			fprintf(stderr, "Could not add RRSIG to zone!\n");
-			return;
-		}
-		tmp = tmp->next;
-	}
-}
-
-static void process_error(const scanner_t *s)
-{
-	err_count++;
-	if (s->stop == true) {
-		printf("ERROR=%s\n", knot_strerror(s->error_code));
-	} else {
-		printf("WARNG=%s\n", knot_strerror(s->error_code));
-	}
-	fflush(stdout);
-}
-
-// TODO this could be a part of the cycle below, but we'd need a buffer.
-static size_t calculate_item_size(const knot_rrset_t *rrset,
-                               const scanner_t *scanner)
-{
-	const rdata_descriptor_t *desc = get_rdata_descriptor(rrset->type);
-	assert(desc);
-	size_t size = 0;
-	for (int i = 0; desc->block_types[i] != KNOT_RDATA_WF_END; i++) {
-		int item = desc->block_types[i];
-		if (descriptor_item_is_dname(item)) {
-			size += sizeof(knot_dname_t *);
-		} else if (descriptor_item_is_fixed(item)) {
-			assert(item == scanner->r_data_blocks[i + 1] -
-			       scanner->r_data_blocks[i]);
-			size += item;
-		} else if (descriptor_item_is_remainder(item)) {
-			size += scanner->r_data_blocks[i + 1] -
-			        scanner->r_data_blocks[i];
-		} else {
-			//naptr
-			assert(0);
-		}
-	}
-	
-	return size;
-}
-
-static int add_rdata_to_rr(knot_rrset_t *rrset, const scanner_t *scanner)
-{
-	if (rrset == NULL) {
-		dbg_zp("zp: add_rdata_to_rr: No RRSet.\n");
-		return KNOT_EINVAL;
-	}
-	
-	const rdata_descriptor_t *desc =
-		get_rdata_descriptor(knot_rrset_type(rrset));
-	assert(desc);
-	
-	dbg_zp_detail("zp: add_rdata_to_rr: Adding type %d, RRSet has %d RRs.\n",
-	              rrset->type, rrset->rdata_count);
-	
-	size_t rdlen = calculate_item_size(rrset, scanner);
-	size_t offset = 0;
-	uint8_t *rdata = knot_rrset_create_rdata(rrset, rdlen);
-	if (rdata == NULL) {
-		dbg_zp("zp: create_rdata: Could not create RR.\n");
-		return KNOT_ENOMEM;
-	}
-	
-	for (int i = 0; desc->block_types[i] != KNOT_RDATA_WF_END; i++) {
-		int item = desc->block_types[i];
-		if (descriptor_item_is_dname(item)) {
-			/* TODO another function perhaps? */
-			knot_dname_t *dname =
-				knot_dname_new_from_wire(scanner->r_data +
-			                                 scanner->r_data_blocks[i],
-			                                 scanner->r_data_blocks[i + 1] - scanner->r_data_blocks[i],
-			                                 NULL);
-			if (dname == NULL) {
-				//TODO handle
-				return KNOT_ERROR;
-			}
-dbg_zp_exec_detail(
-			char *name = knot_dname_to_str(dname);
-			dbg_zp_detail("zp: arr_rdata_to_rr: "
-			              "Offset=%d:Adding dname=%s (%p)\n",
-			              offset, name, dname);
-			free(name);
-);
-			memcpy(rdata + offset, &dname, sizeof(knot_dname_t *));
-			offset += sizeof(knot_dname_t *);
-			//parse dname from binary
-		} else if (descriptor_item_is_fixed(item)) {
-			//copy the whole thing
-			// TODO check the size
-			assert(item == scanner->r_data_blocks[i + 1] -
-			       scanner->r_data_blocks[i]);
-			memcpy(rdata + offset,
-			       scanner->r_data + scanner->r_data_blocks[i],
-			       item);
-			offset += item;
-		} else if (descriptor_item_is_remainder(item)) {
-			//copy the rest
-			memcpy(rdata + offset,
-			       scanner->r_data + scanner->r_data_blocks[i],
-			       scanner->r_data_blocks[i + 1] -
-			       scanner->r_data_blocks[i]);
-			offset += scanner->r_data_blocks[i + 1] -
-			          scanner->r_data_blocks[i];
-		} else {
-			//NAPTR
-			assert(knot_rrset_type(rrset) == KNOT_RRTYPE_NAPTR);
-			assert(0);
-		}
-	}
-	
-	return KNOT_EOK;
-}
-
-static void process_rr(const scanner_t *scanner)
-{
-	dbg_zp_detail("Owner from parser=%s\n",
-	              scanner->r_owner);
-	rr_count++;
-	char add = 0;
-	parser_context_t *parser = scanner->data;
-	knot_zone_contents_t *contents = parser->current_zone;
-	/* Create rrset. TODO will not be always needed. */
-	knot_dname_t *current_owner = NULL;
-	knot_rrset_t *current_rrset = NULL;
-	if (parser->last_node &&
-	    (scanner->r_owner_length == parser->last_node->owner->size) &&
-	    (strncmp((char *)parser->last_node->owner->name,
-	            (char *)scanner->r_owner, scanner->r_owner_length) == 0)) {
-		// no need to create new dname;
-		current_owner = parser->last_node->owner;
-		// what about RRSet, do we need a new one?
-		current_rrset = knot_node_get_rrset(parser->last_node,
-		                                    scanner->r_type);
-		if (current_rrset == NULL) {
-			add = 1;
-			new_rr_count++	;
-			current_rrset =
-				knot_rrset_new(current_owner,
-				               scanner->r_type,
-				               scanner->r_class,
-				               scanner->r_ttl);
-		}
-	} else {
-		add = 1;
-//		if (strncmp((char *)parser->last_node->owner->name,
-//	                (char *)scanner->r_owner, scanner->r_owner_length)) {
-//			new_dname_count++;
-//			current_owner = 
-//		                knot_dname_new_from_wire(scanner->r_owner,
-//	                                         scanner->r_owner_length,
-//	                                         NULL);
-//		} else {
-//			current_owner = parser->last_node->owner;
-//		}
-		current_owner = 
-			knot_dname_new_from_wire(scanner->r_owner,
-			                         scanner->r_owner_length,
-			                         NULL);
-		new_rr_count++;
-		new_dname_count++;
-		current_rrset =
-			knot_rrset_new(current_owner,
-			               scanner->r_type,
-			               scanner->r_class,
-			               scanner->r_ttl);
-		knot_dname_release(current_owner);
-	}
-	
-	assert(current_owner);
-	parser->current_rrset = current_rrset;
-	assert(current_rrset);
-	
-	int ret = add_rdata_to_rr(current_rrset, scanner);
-	assert(ret == 0);
-	
-	dbg_zp_verb("zp: process_rr: Processing type: %s.\n",
-	            knot_rrtype_to_string(parser->current_rrset->type));
-	dbg_zp_verb("zp: process_rr: RDATA count: %d.\n",\
-	            parser->current_rrset->rdata->count);
-
-	assert(current_rrset->rdata_count);
-
-	int (*node_add_func)(knot_zone_contents_t *, knot_node_t *, int,
-	                     uint8_t, int);
-	knot_node_t *(*node_get_func)(const knot_zone_contents_t *,
-	                                const knot_dname_t *);
-
-
-	/* If we have RRSIG of NSEC3 type first node will have
-	 * to be created in NSEC3 part of the zone */
-
-	uint16_t type_covered = 0;
-	if (current_rrset->type == KNOT_RRTYPE_RRSIG) {
-		type_covered =
-			knot_rrset_rdata_rrsig_type_covered(current_rrset);
-	}
-
-	if (current_rrset->type != KNOT_RRTYPE_NSEC3 &&
-	    type_covered != KNOT_RRTYPE_NSEC3) {
-		node_add_func = &knot_zone_contents_add_node;
-		node_get_func = &knot_zone_contents_get_node;
-	} else {
-		node_add_func = &knot_zone_contents_add_nsec3_node;
-		node_get_func = &knot_zone_contents_get_nsec3_node;
-	}
-
-	if (current_rrset->type == KNOT_RRTYPE_SOA) {
-		if (knot_node_rrset(knot_zone_contents_apex(contents),
-		                      KNOT_RRTYPE_SOA) != NULL) {
-			/* Receiving another SOA. */
-			if (!knot_rrset_equal(current_rrset,
-			    knot_node_rrset(knot_zone_contents_apex(contents),
-			    KNOT_RRTYPE_SOA), KNOT_RRSET_COMPARE_WHOLE)) {
-				parser->ret = KNOTDZCOMPILE_ESOA;
-				return;
-			} else {
-				log_zone_warning("encountered identical "
-				                 "extra SOA record");
-				parser->ret = KNOTDZCOMPILE_EOK;
-				return;
-			}
-		}
-	}
-
-	/*!< \todo Make sure the maximum RDLENGTH does not exceed 65535 bytes.*/
-
-	if (current_rrset->type == KNOT_RRTYPE_SOA) {
-		if (knot_dname_compare(current_rrset->owner,
-					parser->origin_from_config) != 0) {
-			fprintf(stderr, "SOA record has a different "
-				"owner than the one specified "
-				"in config! \n");
-			/* Such SOA cannot even be added, because
-			 * it would not be in the zone apex. */
-			parser->ret = KNOTDZCOMPILE_ESOA;
-			return;
-		}
-	}
-
-	if (current_rrset->type == KNOT_RRTYPE_RRSIG) {
-		knot_rrset_t *tmp_rrsig = current_rrset;
-
-		if (parser->last_node &&
-		    knot_dname_compare(parser->last_node->owner,
-		                         current_rrset->owner) != 0) {
-			/* RRSIG is first in the node, so we have to create it
-			 * before we return
-			 */
-			if (parser->node_rrsigs != NULL) {
-				process_rrsigs_in_node(parser,
-				                       contents,
-				                       parser->last_node);
-				rrset_list_delete(&parser->node_rrsigs);
-			}
-			
-			/* The node might however been created previously. */
-			parser->last_node =
-				knot_zone_contents_get_node(contents,
-					knot_rrset_owner(current_rrset));
-			
-			if (parser->last_node == NULL) {
-				/* Try NSEC3 tree. */
-				if (current_rrset->type == KNOT_RRTYPE_NSEC3 ||
-				    current_rrset->type == KNOT_RRTYPE_RRSIG) {
-					parser->last_node =
-						knot_zone_contents_get_nsec3_node(
-							contents,
-							knot_rrset_owner(
-								current_rrset));
-				}
-			}
-			
-			if (parser->last_node == NULL) {
-				/* Still NULL, node has to be created. */
-				if ((parser->last_node = create_node(contents,
-				                                     current_rrset, node_add_func,
-				                                     node_get_func)) == NULL) {
-					knot_rrset_free(&tmp_rrsig);
-					dbg_zp("zp: process_rr: Cannot "
-					       "create new node.\n");
-					parser->ret = KNOTDZCOMPILE_EBADNODE;
-					return;
-				}
-			}
-		}
-
-		if (rrset_list_add(&parser->node_rrsigs, tmp_rrsig) != 0) {
-			dbg_zp("zp: process_rr: Cannot "
-			       "create new node.\n");
-			parser->ret = KNOTDZCOMPILE_ENOMEM;
-			return;
-		}
-		
-		dbg_zp_verb("zp: process_rr: RRSIG proccesed successfully.\n");
-		parser->ret = KNOTDZCOMPILE_EOK;
-		return;
-	}
-	
-	/*! \todo Move RRSIG and RRSet handling to funtions. */
-	assert(current_rrset->type != KNOT_RRTYPE_RRSIG);
-
-	knot_node_t *node = NULL;
-	/* \note this could probably be much simpler */
-	if (parser->last_node && current_rrset->type != KNOT_RRTYPE_SOA &&
-	    knot_dname_compare(parser->last_node->owner,
-				 current_rrset->owner) ==
-	    0) {
-		node = parser->last_node;
-	} else {
-		if (parser->last_node && parser->node_rrsigs) {
-			process_rrsigs_in_node(parser,
-			                       contents,
-			                       parser->last_node);
-		}
-
-		rrset_list_delete(&parser->node_rrsigs);
-
-		/* new node */
-		node = node_get_func(contents, current_rrset->owner);
-	}
-
-	if (node == NULL) {
-		if (parser->last_node && parser->node_rrsigs) {
-			process_rrsigs_in_node(parser,
-			                       contents,
-			                       parser->last_node);
-		}
-
-		if ((node = create_node(contents, current_rrset,
-					node_add_func,
-					node_get_func)) == NULL) {
-			dbg_zp("zp: process_rr: Cannot "
-			       "create new node.\n");
-			parser->ret = KNOTDZCOMPILE_EBADNODE;
-			return;
-		}
-	}
-	
-//	rrset = knot_node_get_rrset(node, current_rrset->type);
-//	if (!rrset) {
-//		rrset = current_rrset;
-//	} else {
-//		merged = 1;
-//	}
-///	if (!rrset) {
-//		int ret = knot_rrset_deep_copy(current_rrset, &rrset, 1);
-//		if (ret != KNOT_EOK) {
-//			dbg_zp("zp: Cannot copy RRSet.\n");
-//			return ret;
-//		}
-//		rrset = knot_rrset_new(current_rrset->owner,
-//					 current_rrset->type,
-//					 current_rrset->rclass,
-//					 current_rrset->ttl);
-//		if (rrset == NULL) {
-//			dbg_zp("zp: process_rr: Cannot "
-//			       "create new RRSet.\n");
-//			return KNOTDZCOMPILE_ENOMEM;
-//		}
-
-//		if (knot_rrset_add_rdata(rrset, current_rrset->rdata) != 0) {
-//			knot_rrset_free(&rrset);
-//			dbg_zp("zp: process_rr: Cannot "
-//			       "add RDATA to RRSet.\n");
-//			return KNOTDZCOMPILE_EBRDATA;
-//		}
-		
-		/* Selected merge option does not really matter here. */
-//		if (knot_zone_contents_add_rrset(contents, current_rrset, &node,
-//		                   KNOT_RRSET_DUPL_MERGE, 1) < 0) {
-//			knot_rrset_free(&rrset);
-//			dbg_zp("zp: process_rr: Cannot "
-//			       "add RDATA to RRSet.\n");
-//			return KNOTDZCOMPILE_EBRDATA;
-//		}
-//	} else {
-//	TODO needs solving
-//	if (current_rrset->type !=
-//			KNOT_RRTYPE_RRSIG && rrset->ttl !=
-//			current_rrset->ttl) {
-//		fprintf(stderr, 
-//			"TTL does not match the TTL of the RRSet. "
-//			"Changing to %d.\n", rrset->ttl);
-//	}
-
-	if (add) {
-		ret = knot_zone_contents_add_rrset(contents, current_rrset,
-		                                   &node,
-		                                   KNOT_RRSET_DUPL_MERGE, 1);
-		if (ret < 0) {
-			dbg_zp("zp: process_rr: Cannot "
-			       "add RRSets.\n");
-			/*!< \todo mixed error codes, has to be changed. */
-			parser->ret = ret;
-			return;
-		} else if (ret > 0) {
-			knot_rrset_deep_free(&current_rrset, 0, 0);
-		}
-	}
-//	}
-
-	parser->last_node = node;
-	
-	dbg_zp_verb("zp: process_rr: RRSet %p processed successfully.\n",
-	            parser->current_rrset);
-	parser->ret = KNOTDZCOMPILE_EOK;
-}
-
-int zone_read(const char *name, const char *zonefile,
-	      int semantic_checks, knot_zone_t **out_zone)
-{
-	parser_context_t my_parser;
-	my_parser.origin_from_config = knot_dname_new_from_str(name,
-	                                                       strnlen((char *)name,
-	                                                               255),
-	                                                       NULL);
-	assert(my_parser.origin_from_config);
-	my_parser.last_node = knot_node_new(my_parser.origin_from_config,
-	                                    NULL, 0);
-	knot_zone_t *zone = knot_zone_new(my_parser.last_node, 0, 0);
-	my_parser.current_zone = knot_zone_get_contents(zone);
-	my_parser.node_rrsigs = NULL;
-	file_loader_t *loader = file_loader_create(zonefile, name,
-	                                           KNOT_CLASS_IN, 3600,
-	                                           process_rr,
-	                                           process_error,
-	                                           &my_parser);
-	file_loader_process(loader);
-	if (my_parser.last_node && my_parser.node_rrsigs) {
-		process_rrsigs_in_node(&my_parser,
-		                       my_parser.current_zone,
-		                       my_parser.last_node);
-	}
-	if (my_parser.ret != KNOTDZCOMPILE_EOK) {
-		log_zone_error("Zone could not be loaded (%d).", my_parser.ret);
-		/*!< \todo Depending on the error, free stuff. */
-		rrset_list_delete(&my_parser.node_rrsigs);
-		file_loader_free(loader);
-		return KNOT_ERROR;
-	}
-	knot_zone_contents_adjust(my_parser.current_zone);
-	rrset_list_delete(&my_parser.node_rrsigs);
-	file_loader_free(loader);
-	*out_zone = zone;
-	return KNOT_EOK;
-}
-
-/*! @} */
diff --git a/src/zcompile/zcompile.h b/src/zcompile/zcompile.h
deleted file mode 100644
index f00d93cae34a8de84e4727397f34283d065a4899..0000000000000000000000000000000000000000
--- a/src/zcompile/zcompile.h
+++ /dev/null
@@ -1,119 +0,0 @@
-/*!
- * \file zoneparser.h
- *
- * \author modifications by Jan Kadlec <jan.kadlec@nic.cz>, most of the code
- *         by NLnet Labs.
- *         Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * \brief Zone compiler.
- *
- * \addtogroup zoneparser
- * @{
- */
-
-/*
- * Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * This software is open source.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- *
- * Neither the name of the NLNET LABS nor the names of its contributors may
- * be used to endorse or promote products derived from this software without
- * specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef _KNOTD_ZONEPARSER_H_
-#define _KNOTD_ZONEPARSER_H_
-
-#include <stdio.h>
-
-#include "libknot/dname.h"
-#include "libknot/rrset.h"
-#include "libknot/zone/node.h"
-#include "libknot/zone/zone.h"
-#include "libknot/zone/dname-table.h"
-#include "libknot/zone/dname-table.h"
-#include "common/slab/slab.h"
-
-#define MAXRDATALEN	64	/*!< Maximum number of RDATA items. */
-#define MAXLABELLEN	63	/*!< Maximum label length. */
-#define MAXDOMAINLEN	255	/*!< Maximum domain name length */
-#define MAX_RDLENGTH	65535	/*!< Maximum length of RDATA item */
-#define	MAXTOKENSLEN	512	/*!< Maximum number of tokens per entry. */
-#define	B64BUFSIZE	65535	/*!< Buffer size for b64 conversion. */
-#define	ROOT		(const uint8_t *)"\001" /*!< Root domain name. */
-
-#define NSEC_WINDOW_COUNT     256	/*!< Number of NSEC windows. */
-#define NSEC_WINDOW_BITS_COUNT 256	/*!< Number of bits in NSEC window. */
-/*! \brief Size of NSEC window in bytes. */
-#define NSEC_WINDOW_BITS_SIZE  (NSEC_WINDOW_BITS_COUNT / 8)
-
-/*
- * RFC 4025 - codes for different types that IPSECKEY can hold.
- */
-#define IPSECKEY_NOGATEWAY      0
-#define IPSECKEY_IP4            1
-#define IPSECKEY_IP6            2
-#define IPSECKEY_DNAME          3
-
-#define LINEBUFSZ 1024	/*!< Buffer size for one line in zone file. */
-
-struct lex_data {
-    size_t   len;		/*!< holds the label length */
-    char    *str;		/*!< holds the data */
-};
-
-#define DEFAULT_TTL 3600
-
-/*! \todo Implement ZoneDB. */
-typedef void namedb_type;
-
-/*!
- * \brief One-purpose linked list holding pointers to RRSets.
- */
-struct rrset_list {
-	knot_rrset_t *data; /*!< List data. */
-	struct rrset_list *next; /*!< Next node. */
-};
-
-typedef struct rrset_list rrset_list_t;
-
-/*!
- * \brief Parses and creates zone from given file.
- *
- * \param name Origin domain name string.
- * \param zonefile File containing the zone.
- * \param outfile File to save dump of the zone to.
- * \param semantic_checks Enables or disables sematic checks.
- *
- * \retval 0 on success.
- * \retval -1 on error.
- */
-int zone_read(const char *name, const char *zonefile, int semantic_checks,
-              knot_zone_t **out_zone);
-
-#endif /* _KNOTD_ZONEPARSER_H_ */
-
-/*! @} */
diff --git a/src/zcompile/zcompile_main.c b/src/zcompile/zcompile_main.c
deleted file mode 100644
index 0818970bcd7f19c042bcc74756c2924ff5a12b5e..0000000000000000000000000000000000000000
--- a/src/zcompile/zcompile_main.c
+++ /dev/null
@@ -1,111 +0,0 @@
-/*  Copyright (C) 2011 CZ.NIC, z.s.p.o. <knot-dns@labs.nic.cz>
-
-    This program is free software: you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation, either version 3 of the License, or
-    (at your option) any later version.
-
-    This program is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with this program.  If not, see <http://www.gnu.org/licenses/>.
- */
-
-#include <config.h>
-#include <unistd.h>
-#include <stdlib.h>
-
-#include "zcompile/zcompile.h"
-#include "common/log.h"
-#include <config.h>
-
-static void help(int argc, char **argv)
-{
-	printf("Usage: %s [parameters] origin zonefile\n",
-	       argv[0]);
-	printf("\n:Parameters:\n"
-	       " -o <outfile> Override output file.\n"
-	       " -v           Verbose mode - additional runtime information.\n"
-	       " -s           Enable semantic checks.\n"
-	       " -V           Print version of the server.\n"
-	       " -h           Print help and usage.\n");
-}
-
-int main(int argc, char **argv)
-{
-	// Parse command line arguments
-	int c = 0;
-	int verbose = 0;
-	int semantic_checks = 0;
-	const char* origin = 0;
-	const char* zonefile = 0;
-	const char* outfile = 0;
-	while ((c = getopt (argc, argv, "o:vVsh")) != -1) {
-		switch (c)
-		{
-		case 'o':
-			outfile = optarg;
-			break;
-		case 'v':
-			verbose = 1;
-			break;
-		case 'V':
-			printf("%s, version %s\n", "Knot DNS", PACKAGE_VERSION);
-			return 0;
-		case 's':
-			semantic_checks = 1;
-			break;
-		case 'h':
-		case '?':
-		default:
-			if (optopt == 'o') {
-				fprintf (stderr,
-					 "Option -%c requires an argument.\n",
-					 optopt);
-			}
-			help(argc, argv);
-			return 1;
-		}
-	}
-
-	UNUSED(verbose);
-
-	// Check if there's at least two remaining non-option
-	if (argc - optind < 2) {
-		help(argc, argv);
-		return 1;
-	}
-
-	origin = argv[optind];
-	zonefile = argv[optind + 1];
-
-	// Initialize log (no syslog)
-	log_init();
-	log_levels_set(LOGT_SYSLOG, LOG_ANY, 0);
-	if (outfile != NULL) {
-		log_zone_info("Parsing file '%s', origin '%s' ...\n",
-		              zonefile, origin);
-	}
-	
-	int error = zone_read(origin, zonefile, outfile, semantic_checks);
-
-	if (error != 0) {
-	  /* FIXME! */
-//		if (error < 0) {
-//			fprintf(stderr, "Finished with error: %s.\n",
-//			       error_to_str(knot_zcompile_error_msgs, error));
-//		} else {
-//			fprintf(stderr, "Finished with %u errors.\n");
-//		}
-		return 1;
-	} else if (outfile != NULL) {
-		log_zone_info("Compilation of '%s' successful.\n", origin);
-	} else {
-		log_zone_info("Zone file for '%s' is OK.\n", origin);
-	}
-	
-	return 0;
-}
diff --git a/src/zcompile/zlexer.l b/src/zcompile/zlexer.l
deleted file mode 100644
index 58e64396472dbebe5ac92417f482d039916fb81a..0000000000000000000000000000000000000000
--- a/src/zcompile/zlexer.l
+++ /dev/null
@@ -1,532 +0,0 @@
-%{
-/*!
- * \file zlexer.l
- *
- * \author minor modifications by Jan Kadlec <jan.kadlec@nic.cz>,
- *         most of the code by NLnet Labs
- *         Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * \brief lexical analyzer for (DNS) zone files.
- *
- * \addtogroup zoneparser
- * @{
- */
-
-/*
- * Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * This software is open source.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- *
- * Neither the name of the NLNET LABS nor the names of its contributors may
- * be used to endorse or promote products derived from this software without
- * specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-//#include "common.h"
-
-#include <ctype.h>
-#include <errno.h>
-#include <string.h>
-#include <strings.h>
-#include <assert.h>
-
-#include "zcompile/zcompile.h"
-#include "libknot/dname.h"
-#include "zcompile/parser-descriptor.h"
-#include "zparser.h"
-
-#define YY_NO_INPUT
-
-/* Utils */
-extern void zc_error(const char *fmt, ...);
-extern void zc_warning(const char *fmt, ...);
-
-void strip_string(char *str)
-{
-	char *start = str;
-	char *end = str + strlen(str) - 1;
-
-	while (isspace(*start))
-		++start;
-	if (start > end) {
-		/* Completely blank. */
-		str[0] = '\0';
-	} else {
-		while (isspace(*end))
-			--end;
-		*++end = '\0';
-
-		if (str != start)
-			memmove(str, start, end - start + 1);
-	}
-}
-
-int hexdigit_to_int(char ch)
-{
-	switch (ch) {
-	case '0': return 0;
-	case '1': return 1;
-	case '2': return 2;
-	case '3': return 3;
-	case '4': return 4;
-	case '5': return 5;
-	case '6': return 6;
-	case '7': return 7;
-	case '8': return 8;
-	case '9': return 9;
-	case 'a': case 'A': return 10;
-	case 'b': case 'B': return 11;
-	case 'c': case 'C': return 12;
-	case 'd': case 'D': return 13;
-	case 'e': case 'E': return 14;
-	case 'f': case 'F': return 15;
-	default:
-		abort();
-	}
-}
-
-extern uint32_t strtottl(const char *nptr, const char **endptr);
-
-#define YY_NO_UNPUT
-#define MAXINCLUDES 10
-
-#define scanner yyscanner
-extern int zp_lex(YYSTYPE *lvalp, void *scanner);
-
-#if 0
-#define LEXOUT(s)  printf s /* used ONLY when debugging */
-#else
-#define LEXOUT(s)
-#endif
-
-enum lexer_state {
-	EXPECT_OWNER,
-	PARSING_OWNER,
-	PARSING_TTL_CLASS_TYPE,
-	PARSING_RDATA
-};
-
-static YY_BUFFER_STATE include_stack[MAXINCLUDES];
-static zparser_type zparser_stack[MAXINCLUDES];
-static int include_stack_ptr = 0;
-
-static void pop_parser_state(void *scanner);
-static void push_parser_state(FILE *input, void *scanner);
-static int parse_token(void *scanner, int token, char *in_str,
-                       enum lexer_state *lexer_state);
-
-
-/*!< \todo does not compile */
-#ifndef yy_set_bol // compat definition, for flex 2.4.6
-#define yy_set_bol(at_bol) \
-{ \
-	if (!yy_current_buffer ) \
-		yy_current_buffer = yy_create_buffer( yyin, YY_BUF_SIZE ); \
-	yy_current_buffer->yy_ch_buf[0] = ((at_bol)?'\n':' '); \
-}
-#endif
-
-%}
-
-%option nounput
-%option reentrant bison-bridge
-%option prefix = "zp_"
-%option outfile = "lex.yy.c"
-
-SPACE   [ \t]
-LETTER  [a-zA-Z]
-NEWLINE [\n\r]
-ZONESTR [^ \t\n\r();.\"\$]
-DOLLAR  \$
-COMMENT ;
-DOT     \.
-BIT     [^\]\n]|\\.
-ANY     [^\"\n\\]|\\.
-
-%x	incl bitlabel quotedstring
-
-%%
-	static int paren_open = 0;
-	static enum lexer_state lexer_state = EXPECT_OWNER;
-
-{SPACE}*{COMMENT}.*	/* ignore */
-^{DOLLAR}TTL            { lexer_state = PARSING_RDATA; return DOLLAR_TTL; }
-^{DOLLAR}ORIGIN         { lexer_state = PARSING_RDATA; return DOLLAR_ORIGIN; }
-
- /*
-  * Handle $INCLUDE directives.  See
-  * http://dinosaur.compilertools.net/flex/flex_12.html#SEC12.
-  */
-^{DOLLAR}INCLUDE        {
-	BEGIN(incl);
-}
-<incl>\n 		|
-<incl><<EOF>>		{
-	int error_occurred = parser->error_occurred;
-	BEGIN(INITIAL);
-	zc_error("missing file name in $INCLUDE directive");
-	yy_set_bol(1); /* Set beginning of line, so "^" rules match.  */
-	++parser->line;
-	parser->error_occurred = error_occurred;
-}
-<incl>.+ 		{
-	char *tmp;
-	/*! \todo pointer to origin. */
-	void *origin = parser->origin;
-	/* domain_type *origin = parser->origin; */
-	int error_occurred = parser->error_occurred;
-
-	BEGIN(INITIAL);
-	if (include_stack_ptr >= MAXINCLUDES ) {
-		zc_error("includes nested too deeply, skipped (>%d)",
-			 MAXINCLUDES);
-	} else {
-		FILE *input;
-
-		/* Remove trailing comment.  */
-		tmp = strrchr(yytext, ';');
-		if (tmp) {
-			*tmp = '\0';
-		}
-		strip_string(yytext);
-
-		/* Parse origin for include file.  */
-		tmp = strrchr(yytext, ' ');
-		if (!tmp) {
-			tmp = strrchr(yytext, '\t');
-		}
-		if (tmp) {
-			/* split the original yytext */
-			*tmp = '\0';
-			strip_string(yytext);
-
-			/*! \todo knot_dname_new_from_wire() (dname.h)
-			 *        which knot_node to pass as node?
-			 */
-			knot_dname_t *dname;
-			dname = knot_dname_new_from_wire((uint8_t*)tmp + 1,
-							   strlen(tmp + 1),
-							   NULL);
-			if (!dname) {
-				zc_error("incorrect include origin '%s'",
-					 tmp + 1);
-			} else {
-				/*! \todo insert to zonedb. */
-				/* origin = domain_table_insert(
-					parser->db->domains, dname); */
-			}
-		}
-
-		if (strlen(yytext) == 0) {
-			zc_error("missing file name in $INCLUDE directive");
-		} else if (!(input = fopen(yytext, "r"))) {
-			char ebuf[256] = {0};
-			strerror_r(errno, ebuf, sizeof(ebuf));
-			zc_error("cannot open include file '%s': %s",
-				 yytext, ebuf);
-		} else {
-			/* Initialize parser for include file.  */
-			char *filename = strdup(yytext);
-			push_parser_state(input, scanner); /* Destroys yytext.  */
-			parser->filename = filename;
-			parser->line = 1;
-			parser->origin = origin;
-			lexer_state = EXPECT_OWNER;
-		}
-	}
-
-	parser->error_occurred = error_occurred;
-}
-<INITIAL><<EOF>>	{
-	yy_set_bol(1); /* Set beginning of line, so "^" rules match.  */
-	if (include_stack_ptr == 0) {
-	// from: http://stackoverflow.com/questions/1756275/bison-end-of-file
-		static int once = 0;
-		once++;
-		if (once > 1) {
-			yyterminate();
-		} else {
-			return NL;
-		}
-	} else {
-		fclose(yyin);
-		pop_parser_state(scanner);
-	}
-}
-^{DOLLAR}{LETTER}+	{ zc_warning("Unknown directive: %s", yytext); }
-{DOT}	{
-	LEXOUT((". "));
-	return parse_token(scanner, '.', yytext, &lexer_state);
-}
-@	{
-	LEXOUT(("@ "));
-	return parse_token(scanner, '@', yytext, &lexer_state);
-}
-\\#	{
-	LEXOUT(("\\# "));
-	return parse_token(scanner, URR, yytext, &lexer_state);
-}
-{NEWLINE}	{
-	++parser->line;
-	if (!paren_open) {
-		lexer_state = EXPECT_OWNER;
-		LEXOUT(("NL\n"));
-		return NL;
-	} else {
-		LEXOUT(("SP "));
-		return SP;
-	}
-}
-\(	{
-	if (paren_open) {
-		zc_error("nested parentheses");
-		yyterminate();
-	}
-	LEXOUT(("( "));
-	paren_open = 1;
-	return SP;
-}
-\)	{
-	if (!paren_open) {
-		zc_error("closing parentheses without opening parentheses");
-		yyterminate();
-	}
-	LEXOUT((") "));
-	paren_open = 0;
-	return SP;
-}
-{SPACE}+	{
-	if (!paren_open && lexer_state == EXPECT_OWNER) {
-		lexer_state = PARSING_TTL_CLASS_TYPE;
-		LEXOUT(("PREV "));
-		return PREV;
-	}
-	if (lexer_state == PARSING_OWNER) {
-		lexer_state = PARSING_TTL_CLASS_TYPE;
-	}
-	LEXOUT(("SP "));
-	return SP;
-}
-
-	/* Bitlabels.  Strip leading and ending brackets.  */
-\\\[			{ BEGIN(bitlabel); }
-<bitlabel><<EOF>>	{
-	zc_error("EOF inside bitlabel");
-	BEGIN(INITIAL);
-}
-<bitlabel>{BIT}*	{ yymore(); }
-<bitlabel>\n		{ ++parser->line; yymore(); }
-<bitlabel>\]		{
-	BEGIN(INITIAL);
-	yytext[yyleng - 1] = '\0';
-	return parse_token(scanner, BITLAB, yytext, &lexer_state);
-}
-
-	/* Quoted strings.  Strip leading and ending quotes.  */
-\"			{ BEGIN(quotedstring); LEXOUT(("\" ")); }
-<quotedstring><<EOF>> 	{
-	zc_error("EOF inside quoted string");
-	BEGIN(INITIAL);
-}
-<quotedstring>{ANY}*	{ LEXOUT(("STR ")); yymore(); }
-<quotedstring>\n 	{ ++parser->line; yymore(); }
-<quotedstring>\" {
-	LEXOUT(("\" "));
-	BEGIN(INITIAL);
-	yytext[yyleng - 1] = '\0';
-	return parse_token(scanner, STR, yytext, &lexer_state);
-}
-
-({ZONESTR}|\\.|\\\n)+ {
-	/* Any allowed word.  */
-	return parse_token(scanner, STR, yytext, &lexer_state);
-}
-. {
-	zc_error("unknown character '%c' (\\%03d) seen - is this a zonefile?",
-		 (int) yytext[0], (int) yytext[0]);
-}
-%%
-
-/*
- * Analyze "word" to see if it matches an RR type, possibly by using
- * the "TYPExxx" notation.  If it matches, the corresponding token is
- * returned and the TYPE parameter is set to the RR type value.
- */
-static int
-rrtype_to_token(const char *word, uint16_t *type)
-{
-	uint16_t t = parser_rrtype_from_string(word);
-	if (t != 0) {
-		parser_rrtype_descriptor_t *entry = 0;
-		entry = parser_rrtype_descriptor_by_type(t);
-		*type = t;
-
-		/*! \todo entry should return associated token.
-			  see nsd/dns.c */
-		return entry->token;
-	}
-
-	return 0;
-}
-
-
-/*
- * Remove \DDD constructs from the input. See RFC 1035, section 5.1.
- */
-static size_t
-zoctet(char *text)
-{
-	/*
-	 * s follows the string, p lags behind and rebuilds the new
-	 * string
-	 */
-	char *s;
-	char *p;
-
-	for (s = p = text; *s; ++s, ++p) {
-		assert(p <= s);
-		if (s[0] != '\\') {
-			/* Ordinary character.  */
-			*p = *s;
-		} else if (isdigit((int)s[1]) && isdigit((int)s[2]) &&  isdigit((int)s[3])) {
-			/* \DDD escape.  */
-			int val = (hexdigit_to_int(s[1]) * 100 +
-				   hexdigit_to_int(s[2]) * 10 +
-				   hexdigit_to_int(s[3]));
-			if (0 <= val && val <= 255) {
-				s += 3;
-				*p = val;
-			} else {
-				zc_warning("text escape \\DDD overflow");
-				*p = *++s;
-			}
-		} else if (s[1] != '\0') {
-			/* \X where X is any character, keep X.  */
-			*p = *++s;
-		} else {
-			/* Trailing backslash, ignore it.  */
-			zc_warning("trailing backslash ignored");
-			--p;
-		}
-	}
-	*p = '\0';
-	return p - text;
-}
-
-static int parse_token(void *scanner, int token, char *in_str,
-                       enum lexer_state *lexer_state)
-{
-	size_t len = 0;
-	char *str = NULL;
-
-	struct yyguts_t *yyg = (struct yyguts_t *)scanner;
-
-	if (*lexer_state == EXPECT_OWNER) {
-		*lexer_state = PARSING_OWNER;
-	} else if (*lexer_state == PARSING_TTL_CLASS_TYPE) {
-		const char *t;
-		int token;
-		uint16_t rrclass;
-
-		/* type */
-		token = rrtype_to_token(in_str, &yylval->type);
-		if (token != 0) {
-			*lexer_state = PARSING_RDATA;
-			LEXOUT(("%d[%s] ", token, in_str));
-			return token;
-		}
-
-		/* class */
-		rrclass = parser_rrclass_from_string(in_str);
-		if (rrclass != 0) {
-			yylval->rclass = rrclass;
-			LEXOUT(("CLASS "));
-			return T_RRCLASS;
-		}
-
-		/* ttl */
-		yylval->ttl = strtottl(in_str, &t);
-		if (*t == '\0') {
-			LEXOUT(("TTL "));
-			return T_TTL;
-		}
-	}
-
-	str = strdup(yytext);
-	if (str == NULL) {
-		/* Out of memory */
-		ERR_ALLOC_FAILED;
-		return NO_MEM;
-	}
-	len = zoctet(str);
-
-	yylval->data.str = str;
-	assert(yylval->data.str != NULL);
-	yylval->data.len = len;
-
-	if (strcmp(yytext, ".") == 0) {
-		free(str);
-		yylval->data.str=".";
-	} else if (strcmp(str, "@") == 0) {
-		free(str);
-		yylval->data.str="@";
-	} else if (strcmp(str, "\\#") == 0) {
-		free(str);
-		yylval->data.str="\\#";
-	}
-
-	LEXOUT(("%d[%s] ", token, in_str));
-	return token;
-}
-
-/*
- * Saves the file specific variables on the include stack.
- */
-static void push_parser_state(FILE *input, void *scanner)
-{
-	struct yyguts_t *yyg = (struct yyguts_t *)scanner;
-	zparser_stack[include_stack_ptr].filename = parser->filename;
-	zparser_stack[include_stack_ptr].line = parser->line;
-	zparser_stack[include_stack_ptr].origin = parser->origin;
-	include_stack[include_stack_ptr] = YY_CURRENT_BUFFER;
-	yy_switch_to_buffer(yy_create_buffer(input, YY_BUF_SIZE, scanner),
-	                    scanner);
-	++include_stack_ptr;
-}
-
-/*
- * Restores the file specific variables from the include stack.
- */
-void pop_parser_state(void *scanner)
-{
-	struct yyguts_t *yyg = (struct yyguts_t *)scanner;
-	--include_stack_ptr;
-	parser->filename = zparser_stack[include_stack_ptr].filename;
-	parser->line = zparser_stack[include_stack_ptr].line;
-	parser->origin = zparser_stack[include_stack_ptr].origin;
-	yy_delete_buffer(YY_CURRENT_BUFFER, scanner);
-	yy_switch_to_buffer(include_stack[include_stack_ptr], scanner);
-}
diff --git a/src/zcompile/zparser.y b/src/zcompile/zparser.y
deleted file mode 100644
index fd0d1b87529597c3f5d8d9b4a6f1a481d7d13cf9..0000000000000000000000000000000000000000
--- a/src/zcompile/zparser.y
+++ /dev/null
@@ -1,1774 +0,0 @@
-%{
-/*!
- * \file zparser.y
- *
- * \author modifications by Jan Kadlec <jan.kadlec@nic.cz>,
- *         notable changes: normal allocation, parser is reentrant.
- *         most of the code by NLnet Labs
- *         Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * \brief yacc grammar for (DNS) zone files
- *
- * \addtogroup zoneparser
- * @{
- */
-
-/*
- * Copyright (c) 2001-2011, NLnet Labs. All rights reserved.
- *
- * This software is open source.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * Redistributions of source code must retain the above copyright notice,
- * this list of conditions and the following disclaimer.
- *
- * Redistributions in binary form must reproduce the above copyright notice,
- * this list of conditions and the following disclaimer in the documentation
- * and/or other materials provided with the distribution.
- *
- * Neither the name of the NLNET LABS nor the names of its contributors may
- * be used to endorse or promote products derived from this software without
- * specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
- * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
- * POSSIBILITY OF SUCH DAMAGE.
- */
-
-//#include "common.h"
-
-#include <stdarg.h>
-#include <stdio.h>
-#include <string.h>
-#include <assert.h>
-
-#include "zcompile/parser-util.h"
-#include "common/log.h"
-
-#include "libknot/libknot.h"
-#include "zcompile/zcompile.h"
-#include "zcompile/parser-descriptor.h"
-#include "zcompile/zcompile-error.h"
-#include "zparser.h"
-
-/* these need to be global, otherwise they cannot be used inside yacc */
-zparser_type *parser;
-
-#ifdef __cplusplus
-extern "C"
-#endif /* __cplusplus */
-int zp_wrap(void);
-
-/* this hold the nxt bits */
-static uint8_t nxtbits[16];
-static int dlv_warn = 1;
-
-/* 256 windows of 256 bits (32 bytes) */
-/* still need to reset the bastard somewhere */
-static uint8_t nsecbits[NSEC_WINDOW_COUNT][NSEC_WINDOW_BITS_SIZE];
-
-/* hold the highest rcode seen in a NSEC rdata , BUG #106 */
-uint16_t nsec_highest_rcode;
-
-void zp_error(void *scanner, const char *message);
-int zp_lex(YYSTYPE *lvalp, void *scanner);
-
-/* helper functions */
-void zc_error(const char *fmt, ...);
-void zc_warning(const char *fmt, ...);
-void zc_error_prev_line(const char *fmt, ...);
-void zc_warning_prev_line(const char *fmt, ...);
-
-#define NSEC3
-#ifdef NSEC3
-/* parse nsec3 parameters and add the (first) rdata elements */
-static void
-nsec3_add_params(const char* hash_algo_str, const char* flag_str,
-	const char* iter_str, const char* salt_str, int salt_len);
-#endif /* NSEC3 */
-
-knot_dname_t *error_dname; //XXX used to be const
-knot_dname_t *error_domain;
-
-%}
-%union {
-	knot_dname_t       *domain;
-	knot_dname_t       *dname;
-	struct lex_data      data;
-	uint32_t             ttl;
-	uint16_t             rclass;
-	uint16_t             type;
-	uint16_t             *unknown;
-}
-
-%pure-parser
-%parse-param {void *scanner}
-%lex-param {void *scanner}
-%name-prefix = "zp_"
-
-/*
- * Tokens to represent the known RR types of DNS.
- */
-%token <type> T_A T_NS T_MX T_TXT T_CNAME T_AAAA T_PTR T_NXT T_KEY T_SOA T_SIG
-%token <type> T_SRV T_CERT T_LOC T_MD T_MF T_MB T_MG T_MR T_NULL T_WKS T_HINFO
-%token <type> T_MINFO T_RP T_AFSDB T_X25 T_ISDN T_RT T_NSAP T_NSAP_PTR T_PX
-%token <type> T_GPOS T_EID T_NIMLOC T_ATMA T_NAPTR T_KX T_A6 T_DNAME T_SINK
-%token <type> T_OPT T_APL T_UINFO T_UID T_GID T_UNSPEC T_TKEY T_TSIG T_IXFR
-%token <type> T_AXFR T_MAILB T_MAILA T_DS T_DLV T_SSHFP T_RRSIG T_NSEC T_DNSKEY
-%token <type> T_SPF T_NSEC3 T_IPSECKEY T_DHCID T_NSEC3PARAM T_TLSA
-
-/* other tokens */
-%token	       DOLLAR_TTL DOLLAR_ORIGIN NL SP NO_MEM
-%token <data>  STR PREV BITLAB
-%token <ttl>   T_TTL
-%token <rclass> T_RRCLASS
-
-/* unknown RRs */
-%token	       URR
-%token <type>  T_UTYPE
-
-%type <type>	type_and_rdata
-%type <domain>	owner dname abs_dname
-%type <dname>	rel_dname label
-%type <data>	wire_dname wire_abs_dname wire_rel_dname wire_label
-%type <data>	concatenated_str_seq str_sp_seq str_dot_seq dotted_str
-%type <data>	nxt_seq nsec_more
-%type <unknown> rdata_unknown
-
-%%
-lines:	/* empty file */
-    |	lines line
-    ;
-
-line:	NL
-    |	sp NL
-    |	NO_MEM {
-    		zc_error_prev_line("Parser ran out of memory!");
-		YYABORT;
-	}
-    |	PREV NL		{}    /* Lines containing only whitespace.  */
-    |	ttl_directive
-	{
-	    parser->error_occurred = 0;
-    }
-    |	origin_directive
-	{
-	    parser->error_occurred = 0;
-    }
-    |	rr
-    {	/* rr should be fully parsed */
-	if (!parser->error_occurred) {
-		/*!< \todo assign error to error occurred */
-		/*! \todo Make sure this does not crash */
-		if (parser->current_rrset->owner == NULL) {
-			knot_rrset_deep_free(&(parser->current_rrset),
-					       0, 0, 0);
-			knot_zone_deep_free(&(parser->current_zone),
-					      1);
-			YYABORT;
-		}
-		knot_rdata_t *tmp_rdata = knot_rdata_new();
-		if (tmp_rdata == NULL) {
-			knot_rrset_deep_free(&(parser->current_rrset),
-					       0, 0, 0);
-			knot_zone_deep_free(&(parser->current_zone),
-					      1);
-			YYABORT;
-		}
-
-		if (knot_rdata_set_items(tmp_rdata,
-		    parser->temporary_items,
-		    parser->rdata_count) != 0) {
-			knot_rdata_free(&tmp_rdata);
-			knot_rrset_deep_free(&(parser->current_rrset), 0, 0, 0);
-			knot_zone_deep_free(&(parser->current_zone), 1);
-			YYABORT;
-		}
-
-		assert(parser->current_rrset->rdata == NULL);
-//		if (knot_rrset_add_rdata(parser->current_rrset, tmp_rdata)
-//		    != 0) {
-//		    	log_zone_error("Could not add rdata!\n");
-//		    }
-//		tmp_rdata->next = tmp_rdata;
-//		parser->current_rrset->rdata = tmp_rdata;
-
-		if (!knot_dname_is_fqdn(parser->current_rrset->owner)) {
-			knot_dname_t *tmp_dname =
-				knot_dname_cat(parser->current_rrset->owner,
-						 parser->root_domain);
-			if (tmp_dname == NULL) {
-				knot_rrset_deep_free(&(parser->current_rrset),
-				                       0, 0, 0);
-				knot_zone_deep_free(&(parser->current_zone),
-				                      1);
-				YYABORT;
-			}
-//			knot_rrset_set_owner(parser->current_rrset, tmp_dname);
-		}
-
-		assert(parser->current_rrset->owner != NULL);
-		knot_dname_retain(parser->current_rrset->owner);
-		int ret = 0;
-		if ((ret = process_rr()) != 0) {
-			char *name =
-				knot_dname_to_str(parser->current_rrset->owner);
-			log_zone_error("Error: could not process RRSet\n"
-				"owner: %s reason: %s\n",
-				name,
-				error_to_str(knot_zcompile_error_msgs, ret));
-			free(name);
-
-			/* If the owner is not already in the table, free it. */
-//			if (dnslib_dname_table_find_dname(parser->dname_table,
-//				parser->current_rrset->owner) == NULL) {
-//				dnslib_dname_free(&parser->
-//				                  current_rrset->owner);
-//			} /* This would never happen */
-
-			if (ret == KNOTDZCOMPILE_EBADSOA) {
-				knot_rrset_deep_free(&(parser->current_rrset),
-						       0, 0, 0);
-				knot_zone_deep_free(&(parser->current_zone),
-						      1);
-				YYABORT;
-			} else {
-				YYABORT;
-				/* Free rdata, it will not be added
-				 * and hence cannot be
-				 * freed with rest of the zone. */
-/*				knot_rdata_deep_free(&tmp_rdata,
-				                       parser->
-				                       current_rrset->type,
-				                       0); */
-			}
-		}
-	} else {
-		/* Error occured. This could either be lack of memory, or one
-		 * of the converting function was not able to convert. */
-		if (parser->error_occurred == KNOTDZCOMPILE_ENOMEM) {
-			/* Ran out of memory in converting functions. */
-			log_zone_error("Parser ran out "
-			                "of memory, aborting!\n");
-			knot_rrset_deep_free(&(parser->current_rrset),
-					       0, 0, 0);
-			knot_zone_deep_free(&(parser->current_zone),
-					      1);
-			YYABORT;
-		}
-	}
-
-//	printf("Current rrset name: %p (%s)\n", parser->current_rrset->owner->name,
-//	knot_dname_to_str(parser->current_rrset->owner));
-
-//	knot_dname_release(parser->current_rrset->owner);
-
-	    parser->current_rrset->type = 0;
-	    parser->rdata_count = 0;
-	    parser->current_rrset->rdata = NULL;
-	    parser->error_occurred = 0;
-    }
-    |	error NL
-    ;
-
-/* needed to cope with ( and ) in arbitary places */
-sp:	SP
-    |	sp SP
-    ;
-
-trail:	NL
-    |	sp NL
-    ;
-
-ttl_directive:	DOLLAR_TTL sp STR trail
-    {
-	parser->default_ttl = zparser_ttl2int($3.str,
-					      &(parser->error_occurred));
-	if (parser->error_occurred == 1) {
-		parser->default_ttl = DEFAULT_TTL;
-		parser->error_occurred = 0;
-	}
-
-	free($3.str);
-    }
-    ;
-
-
-
-origin_directive:	DOLLAR_ORIGIN sp abs_dname trail
-    {
-    /*!< \todo this will leak. */
-	    knot_node_t *origin_node = knot_node_new($3 ,NULL, 0);
-	if (parser->origin != NULL) {
-//		knot_node_free(&parser->origin, 1);
-	}
-	    parser->origin = origin_node;
-    }
-    |	DOLLAR_ORIGIN sp rel_dname trail
-    {
-	    zc_error_prev_line("$ORIGIN directive requires"
-			       "absolute domain name");
-    }
-    ;
-
-rr:	owner classttl type_and_rdata
-    {
-	    /* Save the pointer, it might get freed! */
-	    parser->current_rrset->owner = $1;
-//	    parser->current_rrset->owner = $1;
-//	    printf("new owner assigned: %p\n", $1);
-	    parser->current_rrset->type = $3;
-    }
-	;
-
-owner:	dname sp
-    {
-//    	char *name = knot_dname_to_str($1);
-//	printf("Totally new dname: %p %s\n", $1,
-//	name);
-//	free(name);
-	if (parser->prev_dname != NULL) {
-	//	knot_dname_release(parser->prev_dname);
-	}
-	parser->prev_dname = $1;//knot_dname_deep_copy($1);
-	knot_dname_retain(parser->prev_dname);
-	$$ = $1;
-    }
-    |	PREV
-    {
-//	    printf("Name from prev_dname!: %p %s\n", parser->prev_dname,
-//	    knot_dname_to_str(parser->prev_dname));
-	    knot_dname_retain(parser->prev_dname);
-	    $$ = parser->prev_dname;//knot_dname_deep_copy(parser->prev_dname);
-    }
-    ;
-
-classttl:	/* empty - fill in the default, def. ttl and IN class */
-    {
-	    parser->current_rrset->ttl = parser->default_ttl;
-	    parser->current_rrset->rclass = parser->default_class;
-    }
-    |	T_RRCLASS sp		/* no ttl */
-    {
-	    parser->current_rrset->ttl = parser->default_ttl;
-	    parser->current_rrset->rclass = $1;
-    }
-    |	T_TTL sp		/* no class */
-    {
-	    parser->current_rrset->ttl = $1;
-	    parser->current_rrset->rclass = parser->default_class;
-    }
-    |	T_TTL sp T_RRCLASS sp	/* the lot */
-    {
-	    parser->current_rrset->ttl = $1;
-	    parser->current_rrset->rclass = $3;
-    }
-    |	T_RRCLASS sp T_TTL sp	/* the lot - reversed */
-    {
-	    parser->current_rrset->ttl = $3;
-	    parser->current_rrset->rclass = $1;
-    }
-    ;
-
-dname:	abs_dname
-    |	rel_dname
-    {
-	    if ($1 == error_dname) {
-		    $$ = error_domain;
-	    } else if ($1->size + parser->origin->owner->size - 1 >
-		       MAXDOMAINLEN) {
-		    zc_error("domain name exceeds %d character limit",
-			     MAXDOMAINLEN);
-		    $$ = error_domain;
-	    } else {
-		    $$ = knot_dname_cat($1,
-					  parser->origin->owner);
-	    }
-    }
-    ;
-
-abs_dname:	'.'
-    {
-	    $$ = parser->root_domain;
-	    /* TODO how about concatenation now? */
-    }
-    |	'@'
-    {
-    	assert(parser->origin != NULL);
-	$$ = parser->origin->owner;
-    }
-    |	rel_dname '.'
-    {
-	    if ($1 != error_dname) {
-		    $$ = $1;
-	    } else {
-		    $$ = error_domain;
-	    }
-    }
-    ;
-
-label:	STR
-    {
-	    if ($1.len > MAXLABELLEN) {
-		    zc_error("label exceeds %d character limit", MAXLABELLEN);
-		    $$ = error_dname;
-	    } else {
-		    $$ = knot_dname_new_from_str($1.str, $1.len, NULL);
-	$$->ref.count = 0;
-	    }
-
-	    free($1.str);
-
-    }
-    |	BITLAB
-    {
-	    zc_error("bitlabels are not supported."
-		     "RFC2673 has status experimental.");
-	    $$ = error_dname;
-    }
-    ;
-
-rel_dname:	label
-    |	rel_dname '.' label
-    {
-	    if ($1 == error_dname || $3 == error_dname) {
-		    $$ = error_dname;
-	    } else if ($1->size + $3->size - 1 > MAXDOMAINLEN) {
-		    zc_error("domain name exceeds %d character limit",
-			     MAXDOMAINLEN);
-		    $$ = error_dname;
-	    } else {
-		    $$ = knot_dname_cat($1, $3);
-//		    knot_dname_release($1); /*!< \todo check! */
-		    knot_dname_free(&$3);
-		}
-    }
-    ;
-
-/*
- * Some dnames in rdata are handled as opaque blobs
- */
-
-wire_dname:	wire_abs_dname
-    |	wire_rel_dname
-    ;
-
-wire_abs_dname:	'.'
-    {
-	    char *result = malloc(2 * sizeof(char));
-	    if (result == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    result[0] = 0;
-	    result[1] = '\0';
-	    $$.str = result;
-	    $$.len = 1;
-    }
-    |	wire_rel_dname '.'
-    {
-	    char *result = malloc($1.len + 2 * sizeof(char));
-	    if (result == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    memcpy(result, $1.str, $1.len);
-	    result[$1.len] = 0;
-	    result[$1.len+1] = '\0';
-	    $$.str = result;
-	    $$.len = $1.len + 1;
-
-	    free($1.str);
-;
-    }
-    ;
-
-wire_label:	STR
-    {
-	    char *result = malloc($1.len + sizeof(char));
-	    if (result == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-
-	    if ($1.len > MAXLABELLEN)
-		    zc_error("label exceeds %d character limit", MAXLABELLEN);
-
-	    /* make label anyway */
-	    result[0] = $1.len;
-	    memcpy(result+1, $1.str, $1.len);
-
-	    $$.str = result;
-	    $$.len = $1.len + 1;
-
-	    free($1.str);
-    }
-    ;
-
-wire_rel_dname:	wire_label
-    |	wire_rel_dname '.' wire_label
-    {
-	    if ($1.len + $3.len - 3 > MAXDOMAINLEN)
-		    zc_error("domain name exceeds %d character limit",
-			     MAXDOMAINLEN);
-
-	    /* make dname anyway */
-	    $$.len = $1.len + $3.len;
-	    $$.str = malloc($$.len + sizeof(char));
-	    if ($$.str == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-		knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    memcpy($$.str, $1.str, $1.len);
-	    memcpy($$.str + $1.len, $3.str, $3.len);
-	    $$.str[$$.len] = '\0';
-
-	    free($1.str);
-	    free($3.str);
-    }
-    ;
-
-
-
-str_seq:	STR
-    {
-	    zadd_rdata_txt_wireformat(zparser_conv_text($1.str, $1.len), 1);
-
-	    if(strcmp($1.str, ".") && strcmp($1.str, "@")
-                && strcmp($1.str, "\\#")) {		// Lexer freed that
-	    	free($1.str);
-            }
-    }
-    |	str_seq sp STR
-    {
-	    zadd_rdata_txt_wireformat(zparser_conv_text($3.str, $3.len), 0);
-
-	    if(strcmp($3.str, ".") && strcmp($3.str, "@")
-                && strcmp($3.str, "\\#")) {		// Lexer freed that
-	    	free($3.str);
-            }
-    }
-    ;
-
-/*
- * Generate a single string from multiple STR tokens, separated by
- * spaces or dots.
- */
-concatenated_str_seq:	STR
-    |	'.'
-    {
-	    $$.len = 1;
-	    $$.str = strdup(".");
-    }
-    |	concatenated_str_seq sp STR
-    {
-	    $$.len = $1.len + $3.len + 1;
-	    $$.str = malloc($$.len + 1);
-	    if ($$.str == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-
-	    memcpy($$.str, $1.str, $1.len);
-	    memcpy($$.str + $1.len, " ", 1);
-	    memcpy($$.str + $1.len + 1, $3.str, $3.len);
-	    $$.str[$$.len] = '\0';
-
-	    free($1.str);
-	    free($3.str);
-    }
-    |	concatenated_str_seq '.' STR
-    {
-	    $$.len = $1.len + $3.len + 1;
-	    $$.str = malloc($$.len + 1);
-	    if ($$.str == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    memcpy($$.str, $1.str, $1.len);
-	    memcpy($$.str + $1.len, ".", 1);
-	    memcpy($$.str + $1.len + 1, $3.str, $3.len);
-
-	    free($1.str);
-	    free($3.str);
-
-	    $$.str[$$.len] = '\0';
-    }
-    ;
-
-/* used to convert a nxt list of types */
-nxt_seq:	STR
-    {
-	    uint16_t type = knot_rrtype_from_string($1.str);
-	    if (type != 0 && type < 128) {
-		    set_bit(nxtbits, type);
-	    } else {
-		    zc_error("bad type %d in NXT record", (int) type);
-	    }
-
-	    free($1.str);
-    }
-    |	nxt_seq sp STR
-    {
-	    uint16_t type = knot_rrtype_from_string($3.str);
-	    if (type != 0 && type < 128) {
-		    set_bit(nxtbits, type);
-	    } else {
-		    zc_error("bad type %d in NXT record", (int) type);
-	    }
-
-	    free($3.str);
-    }
-    ;
-
-nsec_more:	SP nsec_more
-    {
-    }
-    |	NL
-    {
-    }
-    |	STR nsec_seq
-    {
-	    uint16_t type = knot_rrtype_from_string($1.str);
-	    if (type != 0) {
-		    if (type > nsec_highest_rcode) {
-			    nsec_highest_rcode = type;
-		    }
-		    set_bitnsec(nsecbits, type);
-	    } else {
-		    zc_error("bad type %d in NSEC record", (int) type);
-	    }
-
-	    free($1.str);
-    }
-    ;
-
-nsec_seq:	NL
-	|	SP nsec_more
-	;
-
-/*
- * Sequence of STR tokens separated by spaces.	The spaces are not
- * preserved during concatenation.
- */
-str_sp_seq:	STR
-    |	str_sp_seq sp STR
-    {
-	    char *result = malloc($1.len + $3.len + 1);
-	    if (result == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	log_zone_error("Parser ran out of memory, aborting!\n");
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    memcpy(result, $1.str, $1.len);
-	    memcpy(result + $1.len, $3.str, $3.len);
-	    $$.str = result;
-	    $$.len = $1.len + $3.len;
-	    $$.str[$$.len] = '\0';
-
-	    free($1.str);
-	    free($3.str);
-    }
-    ;
-
-/*
- * Sequence of STR tokens separated by dots.  The dots are not
- * preserved during concatenation.
- */
-str_dot_seq:	STR
-    |	str_dot_seq '.' STR
-    {
-	    char *result = malloc($1.len + $3.len + 1);
-	    if (result == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	log_zone_error("Parser ran out of memory, aborting!\n");
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    memcpy(result, $1.str, $1.len);
-	    memcpy(result + $1.len, $3.str, $3.len);
-	    $$.str = result;
-	    $$.len = $1.len + $3.len;
-	    $$.str[$$.len] = '\0';
-
-	    free($1.str);
-	    free($3.str);
-    }
-    ;
-
-/*
- * A string that can contain dots.
- */
-dotted_str:	STR
-    |	'.'
-    {
-	$$.str = ".";
-	$$.len = 1;
-    }
-    |	dotted_str '.'
-    {
-	    char *result = malloc($1.len + 2);
-	    if (result == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	log_zone_error("Parser ran out of memory, aborting!\n");
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    memcpy(result, $1.str, $1.len);
-	    result[$1.len] = '.';
-	    $$.str = result;
-	    $$.len = $1.len + 1;
-	    $$.str[$$.len] = '\0';
-
-	    free($1.str);
-    }
-    |	dotted_str '.' STR
-    {
-	    char *result = malloc($1.len + $3.len + 2);
-	    if (result == NULL) {
-	    	ERR_ALLOC_FAILED;
-	    	log_zone_error("Parser ran out of memory, aborting!\n");
-	    	knot_rrset_deep_free(&(parser->current_rrset),
-		                       0, 0, 0);
-	        knot_zone_deep_free(&(parser->current_zone),
-		                      1);
-		YYABORT;
-	    }
-	    memcpy(result, $1.str, $1.len);
-	    result[$1.len] = '.';
-	    memcpy(result + $1.len + 1, $3.str, $3.len);
-	    $$.str = result;
-	    $$.len = $1.len + $3.len + 1;
-	    $$.str[$$.len] = '\0';
-
-
-	    free($1.str);
-	    free($3.str);
-    }
-    ;
-
-/* define what we can parse */
-type_and_rdata:
-    /*
-     * All supported RR types.	We don't support NULL and types marked obsolete.
-     */
-	T_A sp rdata_a
-    |	T_A sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_NS sp rdata_domain_name
-    |	T_NS sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_MD sp rdata_domain_name { zc_warning_prev_line("MD is obsolete"); }
-    |	T_MD sp rdata_unknown
-    {
-	    zc_warning_prev_line("MD is obsolete");
-	    $$ = $1; parse_unknown_rdata($1, $3);
-    }
-    |	T_MF sp rdata_domain_name { zc_warning_prev_line("MF is obsolete"); }
-    |	T_MF sp rdata_unknown
-    {
-	    zc_warning_prev_line("MF is obsolete");
-	    $$ = $1;
-	    parse_unknown_rdata($1, $3);
-    }
-    |	T_CNAME sp rdata_domain_name
-    |	T_CNAME sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_SOA sp rdata_soa
-    |	T_SOA sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_MB sp rdata_domain_name { zc_warning_prev_line("MB is obsolete"); }
-    |	T_MB sp rdata_unknown
-    {
-	    zc_warning_prev_line("MB is obsolete");
-	    $$ = $1;
-	    parse_unknown_rdata($1, $3);
-    }
-    |	T_MG sp rdata_domain_name
-    |	T_MG sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_MR sp rdata_domain_name
-    |	T_MR sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-      /* NULL */
-    |	T_WKS sp rdata_wks
-    |	T_WKS sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_PTR sp rdata_domain_name
-    |	T_PTR sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_HINFO sp rdata_hinfo
-    |	T_HINFO sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_MINFO sp rdata_minfo /* Experimental */
-    |	T_MINFO sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_MX sp rdata_mx
-    |	T_MX sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_TXT sp rdata_txt
-    |	T_TXT sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_SPF sp rdata_txt
-    |	T_SPF sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_RP sp rdata_rp		/* RFC 1183 */
-    |	T_RP sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_AFSDB sp rdata_afsdb	/* RFC 1183 */
-    |	T_AFSDB sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_X25 sp rdata_x25	/* RFC 1183 */
-    |	T_X25 sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_ISDN sp rdata_isdn	/* RFC 1183 */
-    |	T_ISDN sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_IPSECKEY sp rdata_ipseckey	/* RFC 4025 */
-    |	T_IPSECKEY sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_DHCID sp rdata_dhcid
-    |	T_DHCID sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_RT sp rdata_rt		/* RFC 1183 */
-    |	T_RT sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_NSAP sp rdata_nsap	/* RFC 1706 */
-    |	T_NSAP sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_SIG sp rdata_rrsig
-    |	T_SIG sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_KEY sp rdata_dnskey
-    |	T_KEY sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_PX sp rdata_px		/* RFC 2163 */
-    |	T_PX sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_AAAA sp rdata_aaaa
-    |	T_AAAA sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_LOC sp rdata_loc
-    |	T_LOC sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_NXT sp rdata_nxt
-    |	T_NXT sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_SRV sp rdata_srv
-    |	T_SRV sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_NAPTR sp rdata_naptr	/* RFC 2915 */
-    |	T_NAPTR sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_KX sp rdata_kx		/* RFC 2230 */
-    |	T_KX sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_CERT sp rdata_cert	/* RFC 2538 */
-    |	T_CERT sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_DNAME sp rdata_domain_name /* RFC 2672 */
-    |	T_DNAME sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_APL trail		/* RFC 3123 */
-    |	T_APL sp rdata_apl	/* RFC 3123 */
-    |	T_APL sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_DS sp rdata_ds
-    |	T_DS sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_DLV sp rdata_dlv
-    {
-	    if (dlv_warn) {
-		    dlv_warn = 0;
-		    zc_warning_prev_line("DLV is experimental");
-	    }
-    }
-    |	T_DLV sp rdata_unknown
-    {
-	    if (dlv_warn) {
-		    dlv_warn = 0;
-		    zc_warning_prev_line("DLV is experimental");
-	    }
-	    $$ = $1;
-	    parse_unknown_rdata($1, $3);
-    }
-    |	T_SSHFP sp rdata_sshfp
-    |	T_SSHFP sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_RRSIG sp rdata_rrsig
-    |	T_RRSIG sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_NSEC sp rdata_nsec
-    |	T_NSEC sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_NSEC3 sp rdata_nsec3
-    |	T_NSEC3 sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_NSEC3PARAM sp rdata_nsec3_param
-    |	T_NSEC3PARAM sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_TLSA sp rdata_tlsa
-    |	T_TLSA sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_DNSKEY sp rdata_dnskey
-    |	T_DNSKEY sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-    |	T_UTYPE sp rdata_unknown { $$ = $1; parse_unknown_rdata($1, $3); }
-
-    |	STR error NL
-    {
-	    zc_error_prev_line("unrecognized RR type '%s'", $1.str);
-	    free($1.str);
-    }
-    |	NO_MEM
-    {
-    	zc_error_prev_line("parser ran out of memory!");
-    	YYABORT;
-    }
-    ;
-
-/*
- *
- * below are all the definition for all the different rdata
- *
- */
-
-rdata_a:	dotted_str trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_a($1.str));
-	    free($1.str);
-    }
-    ;
-
-rdata_domain_name:	dname trail
-    {
-	    /* convert a single dname record */
-		if ($1 != NULL) {
-			if (!knot_dname_is_fqdn($1)) {
-			knot_dname_cat($1, parser->root_domain);
-//			parser->current_rrset->owner =
-//				knot_dname_cat($1, parser->root_domain);
-			}
-		}
-	    zadd_rdata_domain($1);
-    }
-    ;
-
-rdata_soa:	dname sp dname sp STR sp STR sp STR sp STR sp STR trail
-    {
-	    /* convert the soa data */
-			if (!knot_dname_is_fqdn($1)) {
-			knot_dname_cat($1, parser->root_domain);
-//			parser->current_rrset->owner =
-//				knot_dname_cat($1, parser->root_domain);
-
-		}
-			if (!knot_dname_is_fqdn($3)) {
-			knot_dname_cat($3, parser->root_domain);
-//			parser->current_rrset->owner =
-//				knot_dname_cat($3, parser->root_domain);
-
-		}
-	    zadd_rdata_domain($1);	/* prim. ns */
-	    zadd_rdata_domain($3);	/* email */
-	    zadd_rdata_wireformat(zparser_conv_serial($5.str)); /* serial */
-	    zadd_rdata_wireformat(zparser_conv_period($7.str)); /* refresh */
-	    zadd_rdata_wireformat(zparser_conv_period($9.str)); /* retry */
-	    zadd_rdata_wireformat(zparser_conv_period($11.str)); /* expire */
-	    zadd_rdata_wireformat(zparser_conv_period($13.str)); /* minimum */
-
-	    free($5.str);
-	    free($7.str);
-	    free($9.str);
-	    free($11.str);
-	    free($13.str);
-    }
-    ;
-
-rdata_wks:	dotted_str sp STR sp concatenated_str_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_a($1.str)); /* address */
-	    zadd_rdata_wireformat(zparser_conv_services($3.str, $5.str));
-	    /* protocol and services */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-    }
-    ;
-
-rdata_hinfo:	STR sp STR trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_text($1.str, $1.len)); /* CPU */
-	    zadd_rdata_wireformat(zparser_conv_text($3.str, $3.len)); /* OS*/
-
-	    free($1.str);
-	    free($3.str);
-    }
-    ;
-
-rdata_minfo:	dname sp dname trail
-    {
-				if (!knot_dname_is_fqdn($1)) {
-
-			knot_dname_cat($1, parser->root_domain);
-
-		}
-					if (!knot_dname_is_fqdn($3)) {
-
-			knot_dname_cat($3, parser->root_domain);
-
-		}
-
-	    /* convert a single dname record */
-	    zadd_rdata_domain($1);
-	    zadd_rdata_domain($3);
-    }
-    ;
-
-rdata_mx:	STR sp dname trail
-    {
-					if (!knot_dname_is_fqdn($3)) {
-			knot_dname_cat($3, parser->root_domain);
-		}
-
-	    zadd_rdata_wireformat(zparser_conv_short($1.str));  /* priority */
-	    zadd_rdata_domain($3);	/* MX host */
-
-	    free($1.str);
-    }
-    ;
-
-rdata_txt:	str_seq trail
-    {
-	; //zadd_rdata_txt_clean_wireformat();
-    }
-    ;
-
-/* RFC 1183 */
-rdata_rp:	dname sp dname trail
-    {
-					if (!knot_dname_is_fqdn($1)) {
-			knot_dname_cat($1, parser->root_domain);
-		}
-					if (!knot_dname_is_fqdn($3)) {
-			knot_dname_cat($3, parser->root_domain);
-		}
-
-	    zadd_rdata_domain($1); /* mbox d-name */
-	    zadd_rdata_domain($3); /* txt d-name */
-    }
-    ;
-
-/* RFC 1183 */
-rdata_afsdb:	STR sp dname trail
-    {
-					if (!knot_dname_is_fqdn($3)) {
-			knot_dname_cat($3, parser->root_domain);
-		}
-
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* subtype */
-	    zadd_rdata_domain($3); /* domain name */
-
-	    free($1.str);
-    }
-    ;
-
-/* RFC 1183 */
-rdata_x25:	STR trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_text($1.str, $1.len));
-	    /* X.25 address. */
-
-	    free($1.str);
-    }
-    ;
-
-/* RFC 1183 */
-rdata_isdn:	STR trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_text($1.str, $1.len));
-	    /* address */
-
-	    free($1.str);
-    }
-    |	STR sp STR trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_text($1.str, $1.len));
-	    /* address */
-	    zadd_rdata_wireformat(zparser_conv_text($3.str, $3.len));
-	    /* sub-address */
-
-	    free($1.str);
-	    free($3.str);
-    }
-    ;
-
-/* RFC 1183 */
-rdata_rt:	STR sp dname trail
-    {
-						if (!knot_dname_is_fqdn($3)) {
-			knot_dname_cat($3, parser->root_domain);
-		}
-
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* preference */
-	    zadd_rdata_domain($3); /* intermediate host */
-
-	    free($1.str);
-    }
-    ;
-
-/* RFC 1706 */
-rdata_nsap:	str_dot_seq trail
-    {
-	    /* String must start with "0x" or "0X".	 */
-	    if (strncasecmp($1.str, "0x", 2) != 0) {
-		    zc_error_prev_line("NSAP rdata must start with '0x'");
-	    } else {
-		    zadd_rdata_wireformat(zparser_conv_hex($1.str + 2,
-							   $1.len - 2));
-		    /* NSAP */
-	    }
-
-	    free($1.str);
-    }
-    ;
-
-/* RFC 2163 */
-rdata_px:	STR sp dname sp dname trail
-    {
-			if (!knot_dname_is_fqdn($3)) {
-				knot_dname_cat($3, parser->root_domain);
-		}
-					if (!knot_dname_is_fqdn($5)) {
-				knot_dname_cat($5, parser->root_domain);
-		}
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* preference */
-	    zadd_rdata_domain($3); /* MAP822 */
-	    zadd_rdata_domain($5); /* MAPX400 */
-
-	    free($1.str);
-    }
-    ;
-
-rdata_aaaa:	dotted_str trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_aaaa($1.str));
-	    /* IPv6 address */
-
-	    free($1.str);
-    }
-    ;
-
-rdata_loc:	concatenated_str_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_loc($1.str)); /* Location */
-
-	    free($1.str);
-    }
-    ;
-
-rdata_nxt:	dname sp nxt_seq trail
-    {
-				if (!knot_dname_is_fqdn($1)) {
-				knot_dname_cat($1, parser->root_domain);
-		}
-	    zadd_rdata_domain($1); /* nxt name */
-	    zadd_rdata_wireformat(zparser_conv_nxt(nxtbits)); /* nxt bitlist */
-	    memset(nxtbits, 0, sizeof(nxtbits));
-    }
-    ;
-
-rdata_srv:	STR sp STR sp STR sp dname trail
-    {
-				if (!knot_dname_is_fqdn($7)) {
-				knot_dname_cat($7, parser->root_domain);
-
-		}
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* prio */
-	    zadd_rdata_wireformat(zparser_conv_short($3.str)); /* weight */
-	    zadd_rdata_wireformat(zparser_conv_short($5.str)); /* port */
-	    zadd_rdata_domain($7); /* target name */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-    }
-    ;
-
-/* RFC 2915 */
-rdata_naptr:	STR sp STR sp STR sp STR sp STR sp dname trail
-    {
-				if (!knot_dname_is_fqdn($11)) {
-				knot_dname_cat($11, parser->root_domain);
-
-		}
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* order */
-	    zadd_rdata_wireformat(zparser_conv_short($3.str)); /* preference */
-	    zadd_rdata_wireformat(zparser_conv_text($5.str, $5.len));
-	    /* flags */
-	    zadd_rdata_wireformat(zparser_conv_text($7.str, $7.len));
-	    /* service */
-	    zadd_rdata_wireformat(zparser_conv_text($9.str, $9.len));
-	    /* regexp */
-	    zadd_rdata_domain($11); /* target name */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-	    free($9.str);
-    }
-    ;
-
-/* RFC 2230 */
-rdata_kx:	STR sp dname trail
-    {
-				if (!knot_dname_is_fqdn($3)) {
-				knot_dname_cat($3, parser->root_domain);
-		}
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* preference */
-	    zadd_rdata_domain($3); /* exchanger */
-
-	    free($1.str);
-    }
-    ;
-
-/* RFC 2538 */
-rdata_cert:	STR sp STR sp STR sp str_sp_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_certificate_type($1.str));
-	    /* type */
-	    zadd_rdata_wireformat(zparser_conv_short($3.str)); /* key tag */
-	    zadd_rdata_wireformat(zparser_conv_algorithm($5.str));
-	    /* algorithm */
-	    zadd_rdata_wireformat(zparser_conv_b64($7.str));
-	    /* certificate or CRL */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-    }
-    ;
-
-/* RFC 3123 */
-rdata_apl:	rdata_apl_seq trail
-    ;
-
-rdata_apl_seq:	dotted_str
-    {
-	    zadd_rdata_txt_wireformat(zparser_conv_apl_rdata($1.str), 1);
-
-	    free($1.str);
-    }
-    |	rdata_apl_seq sp dotted_str
-    {
-	    zadd_rdata_txt_wireformat(zparser_conv_apl_rdata($3.str), 0);
-
-	    free($3.str);
-    }
-    ;
-
-rdata_ds:	STR sp STR sp STR sp str_sp_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* keytag */
-	    zadd_rdata_wireformat(zparser_conv_algorithm($3.str)); /* alg */
-	    zadd_rdata_wireformat(zparser_conv_byte($5.str)); /* type */
-	    zadd_rdata_wireformat(zparser_conv_hex($7.str, $7.len)); /* hash */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-    }
-    ;
-
-rdata_dlv:	STR sp STR sp STR sp str_sp_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* keytag */
-	    zadd_rdata_wireformat(zparser_conv_algorithm($3.str)); /* alg */
-	    zadd_rdata_wireformat(zparser_conv_byte($5.str)); /* type */
-	    zadd_rdata_wireformat(zparser_conv_hex($7.str, $7.len)); /* hash */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-    }
-    ;
-
-rdata_sshfp:	STR sp STR sp str_sp_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_byte($1.str)); /* alg */
-	    zadd_rdata_wireformat(zparser_conv_byte($3.str)); /* fp type */
-	    zadd_rdata_wireformat(zparser_conv_hex($5.str, $5.len)); /* hash */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-    }
-    ;
-
-rdata_dhcid:	str_sp_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_b64($1.str)); /* data blob */
-
-	    free($1.str);
-    }
-    ;
-
-rdata_rrsig:	STR sp STR sp STR sp STR sp STR sp STR
-		sp STR sp wire_dname sp str_sp_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_rrtype($1.str));
-	    /* rr covered */
-	    zadd_rdata_wireformat(zparser_conv_algorithm($3.str)); /* alg */
-	    zadd_rdata_wireformat(zparser_conv_byte($5.str)); /* # labels */
-	    zadd_rdata_wireformat(zparser_conv_period($7.str));
-	    /* # orig TTL */
-	    zadd_rdata_wireformat(zparser_conv_time($9.str)); /* sig exp */
-	    zadd_rdata_wireformat(zparser_conv_time($11.str)); /* sig inc */
-	    zadd_rdata_wireformat(zparser_conv_short($13.str)); /* key id */
-/*	    zadd_rdata_wireformat(zparser_conv_dns_name((const uint8_t*)
-							 $15.str,
-							 $15.len));*/
-	    knot_dname_t *dname =
-		knot_dname_new_from_wire((uint8_t *)$15.str, $15.len, NULL);
-	    knot_dname_retain(dname);
-	    if (dname == NULL) {
-	    	parser->error_occurred = KNOTDZCOMPILE_ENOMEM;
-	    } else {
-	    	knot_dname_cat(dname, parser->root_domain);
-	    }
-
-	    zadd_rdata_domain(dname);
-	    /* sig name */
-	    zadd_rdata_wireformat(zparser_conv_b64($17.str)); /* sig data */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-	    free($9.str);
-	    free($11.str);
-	    free($13.str);
-	    free($15.str);
-	    free($17.str);
-    }
-    ;
-
-rdata_nsec:	wire_dname nsec_seq
-    {
-/*	    zadd_rdata_wireformat(zparser_conv_dns_name((const uint8_t*)
-							$1.str,
-							$1.len));*/
-
-	    knot_dname_t *dname =
-		knot_dname_new_from_wire((uint8_t *)$1.str, $1.len, NULL);
-	    knot_dname_retain(dname);
-	    free($1.str);
-
-	    knot_dname_cat(dname, parser->root_domain);
-
-	    zadd_rdata_domain(dname);
-	    /* nsec name */
-	    zadd_rdata_wireformat(zparser_conv_nsec(nsecbits));
-	    /* nsec bitlist */
-	    memset(nsecbits, 0, sizeof(nsecbits));
-	    nsec_highest_rcode = 0;
-    }
-    ;
-
-rdata_nsec3:   STR sp STR sp STR sp STR sp STR nsec_seq
-    {
-#ifdef NSEC3
-	    nsec3_add_params($1.str, $3.str, $5.str, $7.str, $7.len);
-
-/*	    knot_dname_t *dname =
-		knot_dname_new_from_str($9.str, $9.len, NULL);
-
-	    zadd_rdata_domain(dname); */
-
-	    zadd_rdata_wireformat(zparser_conv_b32($9.str));
-	    /* next hashed name */
-	    zadd_rdata_wireformat(zparser_conv_nsec(nsecbits));
-	    /* nsec bitlist */
-	    memset(nsecbits, 0, sizeof(nsecbits));
-	    nsec_highest_rcode = 0;
-#else
-	    zc_error_prev_line("nsec3 not supported");
-#endif /* NSEC3 */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-	    free($9.str);
-    }
-    ;
-
-rdata_nsec3_param:   STR sp STR sp STR sp STR trail
-    {
-#ifdef NSEC3
-	    nsec3_add_params($1.str, $3.str, $5.str, $7.str, $7.len);
-#else
-	    zc_error_prev_line("nsec3 not supported");
-#endif /* NSEC3 */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-    }
-    ;
-    
-rdata_tlsa:   STR sp STR sp STR sp str_sp_seq trail
-    {
-	zadd_rdata_wireformat(zparser_conv_byte($1.str));
-	zadd_rdata_wireformat(zparser_conv_byte($3.str));
-	zadd_rdata_wireformat(zparser_conv_byte($5.str));
-	zadd_rdata_wireformat(zparser_conv_hex($7.str, $7.len));
-	
-	free($1.str);
-	free($3.str);
-	free($5.str);
-	free($7.str);
-    }
-    ;
-
-rdata_dnskey:	STR sp STR sp STR sp str_sp_seq trail
-    {
-	    zadd_rdata_wireformat(zparser_conv_short($1.str)); /* flags */
-	    zadd_rdata_wireformat(zparser_conv_byte($3.str)); /* proto */
-	    zadd_rdata_wireformat(zparser_conv_algorithm($5.str)); /* alg */
-	    zadd_rdata_wireformat(zparser_conv_b64($7.str)); /* hash */
-
-	    free($1.str);
-	    free($3.str);
-	    free($5.str);
-	    free($7.str);
-    }
-    ;
-
-rdata_ipsec_base: STR sp STR sp STR sp dotted_str
-    {
-	    knot_dname_t* name = 0;
-	    zadd_rdata_wireformat(zparser_conv_byte($1.str)); /* precedence */
-	    zadd_rdata_wireformat(zparser_conv_byte($3.str));
-	    /* gateway type */
-	    zadd_rdata_wireformat(zparser_conv_byte($5.str)); /* algorithm */
-	    switch(atoi($3.str)) {
-		case IPSECKEY_NOGATEWAY:
-			zadd_rdata_wireformat(alloc_rdata_init("", 0));
-			break;
-		case IPSECKEY_IP4:
-			zadd_rdata_wireformat(zparser_conv_a($7.str));
-			break;
-		case IPSECKEY_IP6:
-			zadd_rdata_wireformat(zparser_conv_aaaa($7.str));
-			break;
-		case IPSECKEY_DNAME:
-			/* convert and insert the dname */
-			if(strlen($7.str) == 0)
-				zc_error_prev_line("IPSECKEY must specify"
-						   "gateway name");
-			name = knot_dname_new_from_str($7.str,
-							  strlen($7.str),
-							  NULL);
-			if(!name) {
-				zc_error_prev_line("IPSECKEY bad gateway"
-						   "dname %s", $7.str);
-				knot_rrset_deep_free(&(parser->current_rrset),
-						                          0, 0, 0);
-				knot_zone_deep_free(&(parser->current_zone),
-						      1);
-				YYABORT;
-			}
-
-			if(!knot_dname_is_fqdn(name)) {
-			    assert(parser->origin);
-			    name = knot_dname_cat(name,
-				    parser->origin->owner);
-			    if (name == NULL) {
-			    	zc_error_prev_line("Cannot concatenete dnames, probably run out of memory!\n");
-				YYABORT;
-			    }
-			}
-
-			free($1.str);
-			free($3.str);
-			free($5.str);
-			free($7.str);
-
-			uint16_t* dncpy = malloc(sizeof(uint8_t) * name->size + 2);
-			dncpy[0] = name->size;
-			if (dncpy == NULL) {
-			    ERR_ALLOC_FAILED;
-			    knot_rrset_deep_free(&(parser->current_rrset),
-			                           0, 0, 0);
-			    knot_zone_deep_free(&(parser->current_zone),
-			                          1);
-			    YYABORT;
-			}
-			
-			memcpy((uint8_t *)(dncpy + 1), name->name, name->size);
-			zadd_rdata_wireformat(dncpy);
-			knot_dname_free(&name);
-			break;
-		default:
-			zc_error_prev_line("unknown IPSECKEY gateway type");
-	    }
-    }
-    ;
-
-rdata_ipseckey:	rdata_ipsec_base sp str_sp_seq trail
-    {
-	   zadd_rdata_wireformat(zparser_conv_b64($3.str)); /* public key */
-
-		 free($3.str);
-    }
-    | rdata_ipsec_base trail
-    ;
-
-rdata_unknown:	URR sp STR sp str_sp_seq trail
-    {
-	    /* $2 is the number of octects, currently ignored */
-	    $$ = zparser_conv_hex($5.str, $5.len);
-	    free($5.str);
-	    free($3.str);
-    }
-    |	URR sp STR trail
-    {
-	    $$ = zparser_conv_hex("", 0);
-	    free($3.str);
-    }
-    |	URR error NL
-    {
-	    $$ = zparser_conv_hex("", 0);
-    }
-    ;
-%%
-
-int zp_wrap(void)
-{
-	return 1;
-}
-
-/*
- * Create the parser.
- */
-zparser_type *zparser_create()
-{
-	zparser_type *result = malloc(sizeof(zparser_type));
-	if (result == NULL) {
-	    ERR_ALLOC_FAILED;
-	    return NULL;
-	}
-
-	result->temporary_items = malloc(MAXRDATALEN *
-					  sizeof(knot_rdata_item_t));
-	if (result->temporary_items == NULL) {
-		ERR_ALLOC_FAILED;
-		free(result);
-		return NULL;
-	}
-
-	result->current_rrset = knot_rrset_new(NULL, 0, 0, 0);
-	if (result->current_rrset == NULL) {
-		free(result->temporary_items);
-		free(result);
-		return NULL;
-	}
-
-	result->root_domain = knot_dname_new_from_str(".", 1, NULL);
-	if (result->root_domain == NULL) {
-		free(result->temporary_items);
-		free(result->current_rrset);
-		free(result);
-		return NULL;
-	}
-
-	return result;
-}
-
-/*
- * Initialize the parser for a new zone file.
- */
-void
-zparser_init(const char *filename, uint32_t ttl, uint16_t rclass,
-	     knot_node_t *origin, knot_dname_t *origin_from_config)
-{
-	memset(nxtbits, 0, sizeof(nxtbits));
-	memset(nsecbits, 0, sizeof(nsecbits));
-	nsec_highest_rcode = 0;
-
-	parser->current_zone = NULL;
-	parser->prev_dname = NULL;
-
-	parser->default_ttl = ttl;
-	parser->default_class = rclass;
-
-	parser->origin = origin;
-	parser->prev_dname = NULL;//parser->origin->owner;
-
-	parser->default_apex = origin;
-	parser->error_occurred = 0;
-	parser->errors = 0;
-	parser->line = 1;
-	parser->filename = filename;
-	parser->rdata_count = 0;
-	parser->origin_from_config = origin_from_config;
-	knot_dname_retain(origin_from_config);
-
-	parser->last_node = origin;
-//	parser->root_domain = NULL;
-
-	/* Create zone */
-	parser->current_zone = knot_zone_new(origin, 0, 1);
-
-	parser->node_rrsigs = NULL;
-
-	parser->current_rrset->rclass = parser->default_class;
-	parser->current_rrset->rdata = NULL;
-}
-
-
-void zparser_free()
-{
-	knot_dname_release(parser->root_domain);
-//	knot_dname_release(parser->prev_dname);
-	knot_zone_deep_free(&parser->current_zone, 1);
-	knot_dname_release(parser->origin_from_config);
-	free(parser->temporary_items);
-	if (parser->current_rrset != NULL) {
-		free(parser->current_rrset);
-	}
-	free(parser);
-}
-
-void
-yyerror(void *scanner, const char *message)
-{
-	zc_error("%s", message);
-}
-
-static void
-error_va_list(unsigned line, const char *fmt, va_list args)
-{
-	char sbuf[4096] = {0};
-	size_t buflen = sizeof(sbuf) - 1;
-	char *buf = sbuf;
-	int wb = 0;
-	if (parser->filename) {
-		wb = snprintf(buf, buflen, "%s:%u: ",
-		              parser->filename, line);
-		if (wb > 0) {
-			buf += wb;
-			buflen -= wb;
-		}
-	}
-	
-	wb = vsnprintf(buf, buflen, fmt, args);
-	if (wb > 0) {
-		buf += wb;
-		buflen -= wb;
-		*buf = '\n';
-		*(buf + 1) = '\0';
-	}
-	
-	log_zone_error("%s", sbuf);
-	
-	++parser->errors;
-	parser->error_occurred = 1;
-}
-
-/* the line counting sux, to say the least
- * with this grose hack we try do give sane
- * numbers back */
-void
-zc_error_prev_line(const char *fmt, ...)
-{
-	va_list args;
-	va_start(args, fmt);
-	error_va_list(parser->line - 1, fmt, args);
-	va_end(args);
-}
-
-void
-zc_error(const char *fmt, ...)
-{
-	/* send an error message to stderr */
-	va_list args;
-	va_start(args, fmt);
-	error_va_list(parser->line, fmt, args);
-	va_end(args);
-}
-
-static void
-warning_va_list(unsigned line, const char *fmt, va_list args)
-{
-	char sbuf[4096] = {0};
-	size_t buflen = sizeof(sbuf) - 1;
-	char *buf = sbuf;
-	int wb = 0;
-	if (parser->filename) {
-		wb = snprintf(buf, buflen, "%s:%u: ",
-		              parser->filename, line);
-		if (wb > 0) {
-			buf += wb;
-			buflen -= wb;
-		}
-	}
-
-	wb = vsnprintf(buf, buflen, fmt, args);
-	if (wb > 0) {
-		buf += wb;
-		buflen -= wb;
-		*buf = '\n';
-		*(buf + 1) = '\0';
-	}
-
-	log_zone_warning("%s", sbuf);
-}
-
-void
-zc_warning_prev_line(const char *fmt, ...)
-{
-	va_list args;
-	va_start(args, fmt);
-	warning_va_list(parser->line - 1, fmt, args);
-	va_end(args);
-}
-
-void
-zc_warning(const char *fmt, ... )
-{
-	va_list args;
-	va_start(args, fmt);
-	warning_va_list(parser->line, fmt, args);
-	va_end(args);
-}
-
-#ifdef NSEC3
-static void
-nsec3_add_params(const char* hashalgo_str, const char* flag_str,
-	const char* iter_str, const char* salt_str, int salt_len)
-{
-	zadd_rdata_wireformat(zparser_conv_byte(hashalgo_str));
-	zadd_rdata_wireformat(zparser_conv_byte(flag_str));
-	zadd_rdata_wireformat(zparser_conv_short(iter_str));
-
-	/* salt */
-	if(strcmp(salt_str, "-") != 0)
-		zadd_rdata_wireformat(zparser_conv_hex_length(salt_str,
-							      salt_len));
-	else
-		zadd_rdata_wireformat(alloc_rdata_init("", 1));
-
-}
-#endif /* NSEC3 */