mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Stefan Richter <stefanr@s5r6.in-berlin.de>
To: linux1394-devel@lists.sourceforge.net
Cc: linux-kernel@vger.kernel.org
Subject: PHY pinging test tool
Date: Sat, 17 Jul 2010 19:20:51 +0200 (CEST)	[thread overview]
Message-ID: <tkrat.540ce89bb6307428@s5r6.in-berlin.de> (raw)
In-Reply-To: <tkrat.506ae60f1ea3a97a@s5r6.in-berlin.de>

/*
 * Ping packet transmission test
 *
 * Usage:
 *   - Compile with "gcc test-phy-pinging.c".
 *   - Run with "sudo ./a.out /dev/fw*".
 *   - It will print the ping time to all PHYs and exit.
 */

#include <fcntl.h>
#include <linux/firewire-cdev.h>
#include <poll.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <sys/types.h>

static const char *rcode_to_str(int rcode)
{
	switch (rcode) {
	case RCODE_COMPLETE:		return "complete";
	case RCODE_CONFLICT_ERROR:	return "conflict error";
	case RCODE_DATA_ERROR:		return "data error";
	case RCODE_TYPE_ERROR:		return "type error";
	case RCODE_ADDRESS_ERROR:	return "address error";
	case RCODE_SEND_ERROR:		return "send error";
	case RCODE_CANCELLED:		return "cancelled";
	case RCODE_BUSY:		return "busy";
	case RCODE_GENERATION:		return "generation";
	case RCODE_NO_ACK:		return "no ack";
	}
	return "unknown";
}

static void read_events(int fd)
{
	char buffer[sizeof(struct fw_cdev_event_phy_packet) + 4];
	struct fw_cdev_event_common *ec		= (void *)buffer;
	struct fw_cdev_event_phy_packet *epp	= (void *)buffer;
	ssize_t s = sizeof buffer;
	struct pollfd pfd = {
		.fd	= fd,
		.events	= POLLIN | POLLHUP,
	};

	while (poll(&pfd, 1, 10) > 0) {
		memset(buffer, 0, s);
		s = read(fd, buffer, sizeof buffer);
		if (s < 0) {
			fprintf(stderr, "Failed read: %m\n");
			return;
		}

		switch (ec->type) {
		case FW_CDEV_EVENT_PHY_PACKET_SENT:
			if (epp->rcode == RCODE_COMPLETE)
				printf("PING - phy_id = %d, data = %08x (%.2f us)\n",
				       (int)epp->closure,
				       epp->data[0], epp->data[0] / 49.152);
			else
				printf("PING - phy_id = %d, rcode = %s\n",
				       (int)epp->closure,
				       rcode_to_str(epp->rcode));
			break;
		}
	}
}

static void cooked_ioctl(int fd, int req, void *arg)
{
	if (ioctl(fd, req, arg) < 0)
		fprintf(stderr, "Failed ioctl '%c' 0x%02x: %m\n",
			_IOC_TYPE(req), _IOC_NR(req));
}

void test_phy_pinging(const char *filename)
{
	__u32 rom[5];
	struct fw_cdev_event_bus_reset reset;
	struct fw_cdev_get_info info = {
		.version	= 4,
		.rom		= (unsigned long)rom,
		.rom_length	= sizeof(rom),
		.bus_reset	= (unsigned long)&reset,
	};
	struct fw_cdev_send_phy_packet p;
	int fd, ln, nn, i;

	fd = open(filename, O_RDWR);
	if (fd < 0) {
		fprintf(stderr, "Failed to open %s: %m\n", filename);
		goto out;
	}

	cooked_ioctl(fd, FW_CDEV_IOC_GET_INFO, &info);
	if (reset.node_id != reset.local_node_id) {
		fprintf(stderr, "%s: Not a local node\n", filename);
		goto out_fd;
	}

	p.generation = reset.generation;
	ln = reset.local_node_id & 63;
	nn = (reset.root_node_id & 63) + 1;

	printf("%s: card %d, generation %d, %d nodes, "
	       "local phy_id %d, EUI-64 %08x%08x\n",
	       filename, info.card, reset.generation,
	       nn, ln, rom[3], rom[4]);

	for (i = 0; i < nn; i++) {
		p.closure = i;
		p.data[0] = i << 24;
		p.data[1] = ~p.data[0];
		cooked_ioctl(fd, FW_CDEV_IOC_SEND_PHY_PACKET, &p);
	}

	read_events(fd);
out_fd:
	close(fd);
out:
	printf("\n");
}

int main(int argc, char **argv)
{
	int i;

	if (argc < 2) {
		fprintf(stderr, "Usage: %s /dev/fwX [/dev/fwY ...]\n", argv[0]);
		return 1;
	}

	for (i = 1; i < argc; i++)
		test_phy_pinging(argv[i]);

	return 0;
}



  reply	other threads:[~2010-07-17 17:21 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2010-07-16 20:23 [PATCH 0/4] firewire: 2 simple updates + 2 ABI additions: PHY packet tx/rx Stefan Richter
2010-07-16 20:24 ` [PATCH 1/4] firewire: cdev: some clarifications to the API documentation Stefan Richter
2010-07-17 19:36   ` [PATCH 1/4 update] " Stefan Richter
2010-07-16 20:24 ` [PATCH 2/4] firewire: core: use C99 initializer in array of ioctl handlers Stefan Richter
2010-07-16 20:25 ` [PATCH 3/4 RFC] firewire: cdev: add PHY packet transmission Stefan Richter
2010-07-16 20:25 ` [PATCH 4/4 RFC] firewire: cdev: add PHY packet reception Stefan Richter
2010-07-16 20:28 ` [PATCH libraw1394] Implement raw1394_(start_)phy_packet_write() on new firewire backend Stefan Richter
2010-07-17 17:19 ` [PATCH 5/4 RFC] firewire: cdev: add PHY pinging Stefan Richter
2010-07-17 17:20   ` Stefan Richter [this message]
2010-07-18 11:00   ` Stefan Richter

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=tkrat.540ce89bb6307428@s5r6.in-berlin.de \
    --to=stefanr@s5r6.in-berlin.de \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux1394-devel@lists.sourceforge.net \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®