parser.h revision e918e1383e6e80ba4e4808404999521f984f0b5c
1/*
2 *
3 *  Bluetooth packet analyzer - Common parser functions
4 *
5 *  Copyright (C) 2000-2002  Maxim Krasnyansky <maxk@qualcomm.com>
6 *  Copyright (C) 2003-2004  Marcel Holtmann <marcel@holtmann.org>
7 *
8 *
9 *  This program is free software; you can redistribute it and/or modify
10 *  it under the terms of the GNU General Public License as published by
11 *  the Free Software Foundation; either version 2 of the License, or
12 *  (at your option) any later version.
13 *
14 *  This program is distributed in the hope that it will be useful,
15 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17 *  GNU General Public License for more details.
18 *
19 *  You should have received a copy of the GNU General Public License
20 *  along with this program; if not, write to the Free Software
21 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
22 *
23 *
24 *  $Id$
25 */
26
27#ifndef __PARSER_H
28#define __PARSER_H
29
30struct frame {
31	void	*data;
32	int	data_len;
33	void	*ptr;
34	int	len;
35	int	in;
36	int	handle;
37	int	cid;
38	long	flags;
39	struct	timeval ts;
40};
41
42/* Parser flags */
43#define DUMP_WIDTH	20
44
45#define DUMP_HEX	0x01
46#define DUMP_ASCII	0x02
47#define DUMP_TYPE_MASK	(DUMP_HEX | DUMP_ASCII)
48#define DUMP_TSTAMP	0x04
49#define DUMP_RAW	0x08
50
51/* Parser filter */
52#define FILT_HCI	0x0001
53#define FILT_SCO	0x0002
54#define FILT_L2CAP	0x0004
55#define FILT_RFCOMM	0x0008
56#define FILT_SDP	0x0010
57#define FILT_BNEP	0x0020
58#define FILT_CMTP	0x0040
59#define FILT_HIDP	0x0080
60
61#define FILT_CAPI	0x00010000
62
63#define STRUCT_OFFSET(type, member)  ((uint8_t *)&(((type *)NULL)->member) - \
64                                     (uint8_t *)((type *)NULL))
65
66#define STRUCT_END(type, member)     (STRUCT_OFFSET(type, member) + \
67                                     sizeof(((type *)NULL)->member))
68
69struct parser_t {
70	unsigned long flags;
71	unsigned long filter;
72	unsigned int defpsm;
73	int state;
74};
75
76extern struct parser_t parser;
77
78void init_parser(unsigned long flags, unsigned long filter,
79	unsigned int assume_psm);
80
81static inline int p_filter(unsigned long f)
82{
83	return !(parser.filter & f);
84}
85
86static inline void p_indent(int level, struct frame *f)
87{
88	if (level < 0) {
89		parser.state = 0;
90		return;
91	}
92
93	if (!parser.state) {
94		if (parser.flags & DUMP_TSTAMP)
95			printf("%8lu.%06lu ", f->ts.tv_sec, f->ts.tv_usec);
96		printf("%c ", (f->in ? '>' : '<'));
97		parser.state = 1;
98	} else
99		printf("  ");
100
101	if (level)
102		printf("%*c", (level*2), ' ');
103}
104
105/* get_uXX functions do byte swaping */
106
107/* use memmove to prevent gcc from using builtin memcpy */
108#define get_unaligned(p) \
109	({ __typeof__(*(p)) t; memmove(&t, (p), sizeof(t)); t; })
110
111static inline uint8_t get_u8(struct frame *frm)
112{
113	uint8_t *u8_ptr = frm->ptr;
114	frm->ptr += 1;
115	frm->len -= 1;
116	return *u8_ptr;
117}
118
119static inline uint16_t get_u16(struct frame *frm)
120{
121	uint16_t *u16_ptr = frm->ptr;
122	frm->ptr += 2;
123	frm->len -= 2;
124	return ntohs(get_unaligned(u16_ptr));
125}
126
127static inline uint32_t get_u32(struct frame *frm)
128{
129	uint32_t *u32_ptr = frm->ptr;
130	frm->ptr += 4;
131	frm->len -= 4;
132	return ntohl(get_unaligned(u32_ptr));
133}
134
135static inline uint64_t get_u64(struct frame *frm)
136{
137	uint64_t *u64_ptr = frm->ptr;
138	uint64_t u64 = get_unaligned(u64_ptr), tmp;
139	frm->ptr += 8;
140	frm->len -= 8;
141	tmp = ntohl(u64 & 0xffffffff);
142	u64 = (tmp << 32) | ntohl(u64 >> 32);
143	return u64;
144}
145
146static inline void get_u128(struct frame *frm, uint64_t *l, uint64_t *h)
147{
148	*h = get_u64(frm);
149	*l = get_u64(frm);
150}
151
152char *get_uuid_name(int uuid);
153
154void set_proto(uint16_t handle, uint16_t psm, uint32_t proto);
155uint32_t get_proto(uint16_t handle, uint16_t psm);
156
157void ascii_dump(int level, struct frame *frm, int num);
158void hex_dump(int level, struct frame *frm, int num);
159void raw_dump(int level, struct frame *frm);
160void raw_ndump(int level, struct frame *frm, int num);
161
162void hci_dump(int level, struct frame *frm);
163void l2cap_dump(int level, struct frame *frm);
164void rfcomm_dump(int level, struct frame *frm);
165void sdp_dump(int level, struct frame *frm);
166void bnep_dump(int level, struct frame *frm);
167void cmtp_dump(int level, struct frame *frm);
168void hidp_dump(int level, struct frame *frm);
169
170void capi_dump(int level, struct frame *frm);
171
172static inline void parse(struct frame *frm)
173{
174	p_indent(-1, NULL);
175	if (parser.flags & DUMP_RAW)
176		raw_dump(0, frm);
177	else
178		hci_dump(0, frm);
179	fflush(stdout);
180}
181
182#endif /* __PARSER_H */
183