summaryrefslogtreecommitdiffstats
path: root/commands/ethlog.c
blob: 7885d32c6b47b9790ce8028f72813bbbfb237a4d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
// SPDX-License-Identifier: GPL-2.0-only
// SPDX-FileCopyrightText: (c) 2022 Pengutronix,
//                             Oleksij Rempel <o.rempel@pengutronix.de>

#include <common.h>
#include <command.h>
#include <complete.h>
#include <environment.h>
#include <getopt.h>
#include <net.h>

static void ethlog_rx_monitor(struct eth_device *edev, void *packet,
			       int length)
{
	dev_print_hex_dump(&edev->dev, KERN_DEBUG, "rx data <: ",
			   DUMP_PREFIX_OFFSET, 16, 1, packet, length, true);
	printk("\n");
}

static void ethlog_tx_monitor(struct eth_device *edev, void *packet,
			       int length)
{
	dev_print_hex_dump(&edev->dev, KERN_DEBUG, "tx data >: ",
			   DUMP_PREFIX_OFFSET, 16, 1, packet, length, true);
	printk("\n");
}

static int do_ethlog(int argc, char *argv[])
{
	struct eth_device *edev;
	const char *edevname;
	bool remove = false, promisc = false;
	int opt, ret;

	while ((opt = getopt(argc, argv, "pr")) > 0) {
		switch (opt) {
		case 'p':
			promisc = true;
			break;
		case 'r':
			remove = true;
			break;
		default:
			return COMMAND_ERROR_USAGE;
		}
	}

	if (optind == argc)
		edevname = "eth0";
	else
		edevname = argv[optind];

	edev = eth_get_byname(edevname);
	if (!edev) {
		printf("No such network device: %s\n", edevname);
		return 1;
	}

	if (remove) {
		edev->tx_monitor = NULL;
		edev->rx_monitor = NULL;
		if (promisc)
			eth_set_promisc(edev, false);

		return 0;
	}

	if (promisc) {
		ret = eth_set_promisc(edev, true);
		if (ret)
			dev_warn(&edev->dev, "Failed to set promisc mode: %pe\n",
				 ERR_PTR(ret));
	}

	edev->tx_monitor = ethlog_tx_monitor;
	edev->rx_monitor = ethlog_rx_monitor;

	return 0;
}

BAREBOX_CMD_HELP_START(ethlog)
BAREBOX_CMD_HELP_TEXT("Options:")
BAREBOX_CMD_HELP_OPT("-r", "remove log handler from Ethernet interface")
BAREBOX_CMD_HELP_OPT("-p", "Enable promisc mode, or disable if -r is used")
BAREBOX_CMD_HELP_END

BAREBOX_CMD_START(ethlog)
	.cmd		= do_ethlog,
	BAREBOX_CMD_DESC("ETHLOG - tool to get dump of Ethernet packets")
	BAREBOX_CMD_OPTS("[-rp] [device]")
	BAREBOX_CMD_GROUP(CMD_GRP_NET)
	BAREBOX_CMD_COMPLETE(eth_complete)
BAREBOX_CMD_END