Subversion Repositories planix.SVN

Rev

Rev 2 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 - 1
#include <u.h>
2
#include <libc.h>
3
#include <ip.h>
4
#include "dat.h"
5
#include "protos.h"
6
 
7
typedef struct Hdr	Hdr;
8
struct Hdr
9
{
10
	uchar	hrd[2];
11
	uchar	pro[2];
12
	uchar	hln;
13
	uchar	pln;
14
	uchar	op[2];
15
	uchar	sha[6];
16
	uchar	spa[4];
17
	uchar	tha[6];
18
	uchar	tpa[4];
19
};
20
 
21
enum
22
{
23
	ARPLEN=	28,
24
};
25
 
26
enum
27
{
28
	Ospa,
29
	Otpa,
30
	Ostpa,
31
	Osha,
32
	Otha,
33
	Ostha,
34
	Opa,
35
};
36
 
37
static Field p_fields[] = 
38
{
39
	{"spa",		Fv4ip,	Ospa,	"protocol source",	} ,
40
	{"tpa",		Fv4ip,	Otpa,	"protocol target",	} ,
41
	{"a",		Fv4ip,	Ostpa,	"protocol source/target",	} ,
42
	{"sha",		Fba,	Osha,	"hardware source",	} ,
43
	{"tha",		Fba,	Otha,	"hardware target",	} ,
44
	{"ah",	 	Fba,	Ostha,	"hardware source/target",	} ,
45
	{0}
46
};
47
 
48
static void
49
p_compile(Filter *f)
50
{
51
	if(f->op == '='){
52
		compile_cmp(arp.name, f, p_fields);
53
		return;
54
	}
55
	sysfatal("unknown arp field: %s", f->s);
56
}
57
 
58
static int
59
p_filter(Filter *f, Msg *m)
60
{
61
	Hdr *h;
62
 
63
	if(m->pe - m->ps < ARPLEN)
64
		return 0;
65
 
66
	h = (Hdr*)m->ps;
67
	m->ps += ARPLEN;
68
 
69
	switch(f->subop){
70
	case Ospa:
71
		return h->pln == 4 && NetL(h->spa) == f->ulv;
72
	case Otpa:
73
		return h->pln == 4 && NetL(h->tpa) == f->ulv;
74
	case Ostpa:
75
		return h->pln == 4 && (NetL(h->tpa) == f->ulv ||
76
			NetL(h->spa) == f->ulv);
77
	case Osha:
78
		return memcmp(h->sha, f->a, h->hln) == 0;
79
	case Otha:
80
		return memcmp(h->tha, f->a, h->hln) == 0;
81
	case Ostha:
82
		return memcmp(h->sha, f->a, h->hln)==0
83
			||memcmp(h->tha, f->a, h->hln)==0;
84
	}
85
	return 0;
86
}
87
 
88
static int
89
p_seprint(Msg *m)
90
{
91
	Hdr *h;
92
 
93
	if(m->pe - m->ps < ARPLEN)
94
		return -1;
95
 
96
	h = (Hdr*)m->ps;
97
	m->ps += ARPLEN;
98
 
99
	/* no next protocol */
100
	m->pr = nil;
101
 
102
	m->p = seprint(m->p, m->e, "op=%1d len=%1d/%1d spa=%V sha=%E tpa=%V tha=%E",
103
			NetS(h->op), h->pln, h->hln,
104
			h->spa, h->sha, h->tpa, h->tha);
105
	return 0;
106
}
107
 
108
Proto arp =
109
{
110
	"arp",
111
	p_compile,
112
	p_filter,
113
	p_seprint,
114
	nil,
115
	nil,
116
	p_fields,
117
	defaultframer,
118
};
119
 
120
Proto rarp =
121
{
122
	"rarp",
123
	p_compile,
124
	p_filter,
125
	p_seprint,
126
	nil,
127
	nil,
128
	p_fields,
129
	defaultframer,
130
};