diff --git a/src/knot/nameserver/process_query.c b/src/knot/nameserver/process_query.c
index 52e1a37bc874151a7b0ed44fca54a24b490fb562..37cb93d2b0f67e9aba38af2ba86d5068442bfd96 100644
--- a/src/knot/nameserver/process_query.c
+++ b/src/knot/nameserver/process_query.c
@@ -315,7 +315,7 @@ static int prepare_answer(const knot_pkt_t *query, knot_pkt_t *resp, knot_proces
 
 	/* If Extended RCODE is set, do not continue with query processing. */
 	if (qdata->rcode_ext != 0) {
-		return KNOT_EMALF;
+		return KNOT_ERROR;
 	}
 
 	/* Update maximal answer size. */
@@ -490,7 +490,7 @@ static int process_query_out(knot_pkt_t *pkt, knot_process_t *ctx)
 finish:
 	/* Default RCODE is SERVFAIL if not specified otherwise. */
 	if (next_state == NS_PROC_FAIL && qdata->rcode == KNOT_RCODE_NOERROR
-	    && qdata->rcode_ext != KNOT_RCODE_BADVERS) {
+	    && qdata->rcode_ext == 0) {
 		qdata->rcode = KNOT_RCODE_SERVFAIL;
 	}
 
diff --git a/src/libknot/packet/pkt.h b/src/libknot/packet/pkt.h
index 3b438f8943cff80ca413b1fb66806933ba56c922..7e7a3fe2e66d940dd753438d8779e9c4c8255f32 100644
--- a/src/libknot/packet/pkt.h
+++ b/src/libknot/packet/pkt.h
@@ -294,6 +294,17 @@ int knot_pkt_parse_section(knot_pkt_t *pkt, unsigned flags);
  */
 int knot_pkt_parse_payload(knot_pkt_t *pkt, unsigned flags);
 
+/*!
+ * \brief Get the Extended RCODE from the packet.
+ *
+ * Extended RCODE is created by using the Extended RCODE field from OPT RR as
+ * higher 8 bits and the RCODE from DNS Header as the lower 4 bits, resulting
+ * in a 12-bit unsigned integer. (See RFC 6891, Section 6.1.3).
+ *
+ * \param pkt Packet to get the response code from.
+ *
+ * \return
+ */
 uint16_t knot_pkt_get_ext_rcode(const knot_pkt_t *pkt);
 
 /*!
diff --git a/src/libknot/rrtype/opt.h b/src/libknot/rrtype/opt.h
index 0d53b5098beacb39b6a729489ac118d78ca235ec..ab13ba287223143ae8d1202cfcb84063c078c1f5 100644
--- a/src/libknot/rrtype/opt.h
+++ b/src/libknot/rrtype/opt.h
@@ -138,6 +138,19 @@ void knot_edns_set_payload(knot_rrset_t *opt_rr, uint16_t payload);
  */
 uint8_t knot_edns_get_ext_rcode(const knot_rrset_t *opt_rr);
 
+/*!
+ * \brief Concatenates OPT RR Extended RCODE field and normal RCODE to get the
+ *        whole Extended RCODE.
+ *
+ * Extended RCODE is created by using the Extended RCODE field from OPT RR as
+ * higher 8 bits and the RCODE from DNS Header as the lower 4 bits, resulting
+ * in a 12-bit unsigned integer. (See RFC 6891, Section 6.1.3).
+ *
+ * \param ext_rcode  Extended RCODE field from OPT RR.
+ * \param rcode      RCODE from DNS Header.
+ *
+ * \return 12-bit Extended RCODE.
+ */
 static inline uint16_t knot_edns_whole_rcode(uint8_t ext_rcode, uint8_t rcode)
 {
 	uint16_t high = ext_rcode;