diff --git a/tools/parser/l2cap.c b/tools/parser/l2cap.c
index 7bb6783..f518baa 100644
--- a/tools/parser/l2cap.c
+++ b/tools/parser/l2cap.c
#include <bluetooth/l2cap.h>
#include "parser.h"
+#include "sdp.h"
typedef struct {
uint16_t handle;
uint16_t cid;
uint16_t psm;
} cid_info;
-#define CID_TABLE_SIZE 20
+#define CID_TABLE_SIZE 20
static cid_info cid_table[2][CID_TABLE_SIZE];
}
for (t = 0; t < 2; t++) {
- for (i=0; i<CID_TABLE_SIZE; i++)
+ for (i = 0; i < CID_TABLE_SIZE; i++)
if (cid_table[t][i].cid == cid[t]) {
cid_table[t][i].cid = 0;
break;
{
register cid_info *table = cid_table[in];
register int i;
-
+
for (i = 0; i < CID_TABLE_SIZE; i++)
if (table[i].cid == cid)
return table[i].psm;
p_indent(level, 0);
while (len > 0) {
l2cap_conf_opt *h = ptr;
-
+
ptr += L2CAP_CONF_OPT_SIZE + h->len;
len -= L2CAP_CONF_OPT_SIZE + h->len;
-
+
switch (h->type) {
case L2CAP_CONF_MTU:
printf("MTU %d ", conf_opt_val(h->val, h->len));
if (p_filter(FILT_L2CAP))
return;
- printf("Disconn req: dcid 0x%4.4x scid 0x%4.4x\n",
+ printf("Disconn req: dcid 0x%4.4x scid 0x%4.4x\n",
btohs(h->dcid), btohs(h->scid));
}
if (p_filter(FILT_L2CAP))
return;
- printf("Echo req: dlen %d\n",
- btohs(cmd->len));
+ printf("Echo req: dlen %d\n", btohs(cmd->len));
raw_dump(level, frm);
}
if (p_filter(FILT_L2CAP))
return;
- printf("Echo rsp: dlen %d\n",
- btohs(cmd->len));
+ printf("Echo rsp: dlen %d\n", btohs(cmd->len));
raw_dump(level, frm);
}
if (p_filter(FILT_L2CAP))
return;
- printf("Info req: dlen %d\n",
- btohs(cmd->len));
+ printf("Info req: dlen %d\n", btohs(cmd->len));
raw_dump(level, frm);
}
if (p_filter(FILT_L2CAP))
return;
- printf("Info rsp: dlen %d\n",
- btohs(cmd->len));
+ printf("Info rsp: dlen %d\n", btohs(cmd->len));
raw_dump(level, frm);
}
} else {
/* Connection oriented channel */
uint16_t psm = get_psm(!frm->in, cid);
+ uint32_t proto;
frm->cid = cid;
if (!p_filter(FILT_L2CAP)) {
p_indent(level, frm);
- printf("L2CAP(d): cid 0x%x len %d [psm %d]\n",
+ printf("L2CAP(d): cid 0x%x len %d [psm %d]\n",
cid, dlen, psm);
level++;
}
raw_dump(level + 1, frm);
break;
- case 4099:
- if (!p_filter(FILT_CMTP))
- cmtp_dump(level, frm);
- else
- raw_dump(level + 1, frm);
- break;
-
default:
- if (p_filter(FILT_L2CAP))
+ proto = get_proto(frm->handle, psm);
+
+ switch (proto) {
+ case SDP_UUID_CMTP:
+ if (!p_filter(FILT_CMTP))
+ cmtp_dump(level, frm);
+ else
+ raw_dump(level + 1, frm);
break;
- raw_dump(level, frm);
+ default:
+ if (p_filter(FILT_L2CAP))
+ break;
+
+ raw_dump(level, frm);
+ break;
+ }
break;
}
}
raw_dump(level, frm);
return;
}
-
+
if (frm->len > (fr->data_len - fr->len)) {
/* Bad fragment */
raw_dump(level, frm);
diff --git a/tools/parser/parser.c b/tools/parser/parser.c
index 02fdcac..2ef56a9 100644
--- a/tools/parser/parser.c
+++ b/tools/parser/parser.c
parser.state = 0;
}
+#define PROTO_TABLE_SIZE 20
+
+static struct {
+ uint16_t handle;
+ uint16_t psm;
+ uint32_t proto;
+} proto_table[PROTO_TABLE_SIZE];
+
+void set_proto(uint16_t handle, uint16_t psm, uint32_t proto)
+{
+ int i, pos = -1;
+
+ if (psm < 0x1000)
+ return;
+
+ for (i = 0; i < PROTO_TABLE_SIZE; i++) {
+ if (proto_table[i].handle == handle && proto_table[i].psm == psm) {
+ pos = i;
+ break;
+ }
+
+ if (pos < 0 && !proto_table[i].handle && !proto_table[i].psm)
+ pos = i;
+ }
+
+ if (pos < 0)
+ return;
+
+ proto_table[pos].handle = handle;
+ proto_table[pos].psm = psm;
+ proto_table[pos].proto = proto;
+}
+
+uint32_t get_proto(uint16_t handle, uint16_t psm)
+{
+ int i, pos = -1;
+
+ for (i = 0; i < PROTO_TABLE_SIZE; i++) {
+ if (proto_table[i].handle == handle && proto_table[i].psm == psm)
+ return proto_table[i].proto;
+
+ if (!proto_table[i].handle && proto_table[i].psm == psm)
+ pos = i;
+ }
+
+ return (pos < 0) ? 0 : proto_table[pos].proto;
+}
+
static inline void hex_dump(int level, struct frame *frm, int num)
{
unsigned char *buf = frm->ptr;
if ((num < 0) || (num > frm->len))
num = frm->len;
- for (i=0, n=1; i<num; i++, n++) {
+ for (i = 0, n = 1; i < num; i++, n++) {
if (n == 1)
p_indent(level, frm);
printf("%2.2X ", buf[i]);
if ((num < 0) || (num > frm->len))
num = frm->len;
- for (i=0, n=1; i<num; i++, n++) {
+ for (i = 0, n = 1; i < num; i++, n++) {
if (n == 1)
p_indent(level, frm);
printf("%1c ", isprint(buf[i]) ? buf[i] : '.');
diff --git a/tools/parser/parser.h b/tools/parser/parser.h
index 05b010b..0c2781e 100644
--- a/tools/parser/parser.h
+++ b/tools/parser/parser.h
/* Parser filter */
#define FILT_HCI 0x0001
-#define FILT_L2CAP 0x0002
-#define FILT_RFCOMM 0x0004
-#define FILT_SDP 0x0008
-#define FILT_SCO 0x0010
+#define FILT_SCO 0x0002
+#define FILT_L2CAP 0x0004
+#define FILT_RFCOMM 0x0008
+#define FILT_SDP 0x0010
#define FILT_BNEP 0x0020
#define FILT_CMTP 0x0040
#define FILT_HIDP 0x0080
char *get_uuid_name(int uuid);
+void set_proto(uint16_t handle, uint16_t psm, uint32_t proto);
+uint32_t get_proto(uint16_t handle, uint16_t psm);
+
void raw_dump(int level, struct frame *frm);
void raw_ndump(int level, struct frame *frm, int num);
void hci_dump(int level, struct frame *frm);
diff --git a/tools/parser/sdp.c b/tools/parser/sdp.c
index d58d70c..c1cb0fe 100644
--- a/tools/parser/sdp.c
+++ b/tools/parser/sdp.c
}
if (psm && *psm > 0 && *psm != 0xffff) {
+ set_proto(frm->handle, *psm, uuid);
*psm = 0xffff;
}