Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

nfc: Add KCOV annotations

Add remote KCOV annotations for NFC processing that is done
in background threads. This enables efficient coverage-guided
fuzzing of the NFC subsystem.

The intention is to add annotations to background threads that
process skb's that were allocated in syscall context
(thus have a KCOV handle associated with the current fuzz test).
This includes nci_recv_frame() that is called by the virtual nci
driver in the syscall context.

Signed-off-by: Dmitry Vyukov <dvyukov@google.com>
Cc: Bongsu Jeon <bongsu.jeon@samsung.com>
Cc: Krzysztof Kozlowski <krzysztof.kozlowski@linaro.org>
Cc: netdev@vger.kernel.org
Signed-off-by: David S. Miller <davem@davemloft.net>

authored by

Dmitry Vyukov and committed by
David S. Miller
7e8cdc97 82fd151d

+13 -2
+7 -1
net/nfc/nci/core.c
··· 24 24 #include <linux/sched.h> 25 25 #include <linux/bitops.h> 26 26 #include <linux/skbuff.h> 27 + #include <linux/kcov.h> 27 28 28 29 #include "../nfc.h" 29 30 #include <net/nfc/nci.h> ··· 1473 1472 skb = skb_dequeue(&ndev->tx_q); 1474 1473 if (!skb) 1475 1474 return; 1475 + kcov_remote_start_common(skb_get_kcov_handle(skb)); 1476 1476 1477 1477 /* Check if data flow control is used */ 1478 1478 if (atomic_read(&conn_info->credits_cnt) != ··· 1489 1487 1490 1488 mod_timer(&ndev->data_timer, 1491 1489 jiffies + msecs_to_jiffies(NCI_DATA_TIMEOUT)); 1490 + kcov_remote_stop(); 1492 1491 } 1493 1492 } 1494 1493 ··· 1500 1497 struct nci_dev *ndev = container_of(work, struct nci_dev, rx_work); 1501 1498 struct sk_buff *skb; 1502 1499 1503 - while ((skb = skb_dequeue(&ndev->rx_q))) { 1500 + for (; (skb = skb_dequeue(&ndev->rx_q)); kcov_remote_stop()) { 1501 + kcov_remote_start_common(skb_get_kcov_handle(skb)); 1504 1502 1505 1503 /* Send copy to sniffer */ 1506 1504 nfc_send_to_raw_sock(ndev->nfc_dev, skb, ··· 1555 1551 if (!skb) 1556 1552 return; 1557 1553 1554 + kcov_remote_start_common(skb_get_kcov_handle(skb)); 1558 1555 atomic_dec(&ndev->cmd_cnt); 1559 1556 1560 1557 pr_debug("NCI TX: MT=cmd, PBF=%d, GID=0x%x, OID=0x%x, plen=%d\n", ··· 1568 1563 1569 1564 mod_timer(&ndev->cmd_timer, 1570 1565 jiffies + msecs_to_jiffies(NCI_CMD_TIMEOUT)); 1566 + kcov_remote_stop(); 1571 1567 } 1572 1568 } 1573 1569
+3 -1
net/nfc/nci/hci.c
··· 14 14 #include <net/nfc/nci.h> 15 15 #include <net/nfc/nci_core.h> 16 16 #include <linux/nfc.h> 17 + #include <linux/kcov.h> 17 18 18 19 struct nci_data { 19 20 u8 conn_id; ··· 410 409 const struct nci_hcp_message *message; 411 410 u8 pipe, type, instruction; 412 411 413 - while ((skb = skb_dequeue(&hdev->msg_rx_queue)) != NULL) { 412 + for (; (skb = skb_dequeue(&hdev->msg_rx_queue)); kcov_remote_stop()) { 413 + kcov_remote_start_common(skb_get_kcov_handle(skb)); 414 414 pipe = NCI_HCP_MSG_GET_PIPE(skb->data[0]); 415 415 skb_pull(skb, NCI_HCI_HCP_PACKET_HEADER_LEN); 416 416 message = (struct nci_hcp_message *)skb->data;
+3
net/nfc/rawsock.c
··· 12 12 #include <net/tcp_states.h> 13 13 #include <linux/nfc.h> 14 14 #include <linux/export.h> 15 + #include <linux/kcov.h> 15 16 16 17 #include "nfc.h" 17 18 ··· 190 189 } 191 190 192 191 skb = skb_dequeue(&sk->sk_write_queue); 192 + kcov_remote_start_common(skb_get_kcov_handle(skb)); 193 193 194 194 sock_hold(sk); 195 195 rc = nfc_data_exchange(dev, target_idx, skb, ··· 199 197 rawsock_report_error(sk, rc); 200 198 sock_put(sk); 201 199 } 200 + kcov_remote_stop(); 202 201 } 203 202 204 203 static int rawsock_sendmsg(struct socket *sock, struct msghdr *msg, size_t len)