summaryrefslogtreecommitdiff
path: root/proto_vlan_q_in_q.c
blob: 72e7b7832886d492fe594f36b15f895154d9a9ac (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
/*
 * netsniff-ng - the packet sniffing beast
 * Copyright 2012 Markus Amend <markus@netsniff-ng.org>, Deutsche Flugsicherung GmbH
 * Subject to the GPL, version 2.
 *
 * http://www.ieee802.org/1/pages/802.1ad.html
 */

#include <stdio.h>
#include <stdint.h>
#include <netinet/in.h>    /* for ntohs() */

#include "proto.h"
#include "protos.h"
#include "dissector_eth.h"
#include "built_in.h"
#include "pkt_buff.h"

struct QinQhdr {
	uint16_t TCI;
	uint16_t TPID;
} __packed;

static void QinQ_full(struct pkt_buff *pkt)
{
	uint16_t tci;
	struct QinQhdr *QinQ = (struct QinQhdr *) pkt_pull(pkt, sizeof(*QinQ));

	if (QinQ == NULL)
		return;

	tci = ntohs(QinQ->TCI);

	tprintf(" [ VLAN QinQ ");
	tprintf("Prio (%d), ", (tci & 0xE000) >> 13);
	tprintf("DEI (%d), ", (tci & 0x1000) >> 12);
	tprintf("ID (%d), ", (tci & 0x0FFF));
	tprintf("Proto (0x%.4x)", ntohs(QinQ->TPID));
	tprintf(" ]\n");

	pkt_set_proto(pkt, &eth_lay2, ntohs(QinQ->TPID));
}

static void QinQ_less(struct pkt_buff *pkt)
{
	uint16_t tci;
	struct QinQhdr *QinQ = (struct QinQhdr *) pkt_pull(pkt, sizeof(*QinQ));

	if (QinQ == NULL)
		return;

	tci = ntohs(QinQ->TCI);

	tprintf(" VLAN%d", (tci & 0x0FFF));

	pkt_set_proto(pkt, &eth_lay2, ntohs(QinQ->TPID));
}

struct protocol QinQ_ops = {
	.key = 0x88a8,
	.print_full = QinQ_full,
	.print_less = QinQ_less,
};
stem takes the writer side. Only that we don't really want to bounce cachelines of the semaphores between CPUs for each write happening. So we implement the reader side of the semaphore as a per-cpu counter and the writer side is implemented using s_writers.frozen superblock field. [AV: microoptimize sb_start_write(); we want it fast in normal case] BugLink: https://bugs.launchpad.net/bugs/897421 Tested-by: Kamal Mostafa <kamal@canonical.com> Tested-by: Peter M. Petrakis <peter.petrakis@canonical.com> Tested-by: Dann Frazier <dann.frazier@canonical.com> Tested-by: Massimo Morana <massimo.morana@canonical.com> Signed-off-by: Jan Kara <jack@suse.cz> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'fs')