2 * Routines for Canon BJNP packet disassembly.
4 * Copyright 2009, Stig Bjorlykke <stig@bjorlykke.org>
8 * Wireshark - Network traffic analyzer
9 * By Gerald Combs <gerald@wireshark.org>
10 * Copyright 1998 Gerald Combs
12 * This program is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU General Public License
14 * as published by the Free Software Foundation; either version 2
15 * of the License, or (at your option) any later version.
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
22 * You should have received a copy of the GNU General Public License
23 * along with this program; if not, write to the Free Software
24 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
31 #include <epan/packet.h>
32 #include <epan/wmem/wmem.h>
34 #define PNAME "Canon BJNP"
38 #define BJNP_PORT1 8611
39 #define BJNP_PORT2 8612
40 #define BJNP_PORT3 8613
41 #define BJNP_PORT4 8614
44 #define PRINTER_COMMAND 0x01
45 #define SCANNER_COMMAND 0x02
46 #define PRINTER_RESPONSE 0x81
47 #define SCANNER_RESPONSE 0x82
50 #define CMD_DISCOVER 0x01
51 #define CMD_PRINT_JOB_DET 0x10
52 #define CMD_CLOSE 0x11
53 #define CMD_GET_STATUS 0x20
54 #define CMD_PRINT 0x21
55 #define CMD_GET_ID 0x30
56 #define CMD_SCAN_JOB 0x32
58 void proto_register_bjnp(void);
59 void proto_reg_handoff_bjnp(void);
61 static int proto_bjnp
= -1;
63 static int hf_bjnp_id
= -1;
64 static int hf_dev_type
= -1;
65 static int hf_cmd_code
= -1;
66 static int hf_seq_no
= -1;
67 static int hf_session_id
= -1;
68 static int hf_payload_len
= -1;
69 static int hf_payload
= -1;
71 static gint ett_bjnp
= -1;
73 static dissector_handle_t bjnp_handle
;
75 static const value_string dev_type_vals
[] = {
76 { PRINTER_COMMAND
, "Printer Command" },
77 { SCANNER_COMMAND
, "Scanner Command" },
78 { PRINTER_RESPONSE
, "Printer Response" },
79 { SCANNER_RESPONSE
, "Scanner Response" },
83 static const value_string cmd_code_vals
[] = {
84 { CMD_DISCOVER
, "Discover" },
85 { CMD_PRINT_JOB_DET
, "Print Job Details" },
86 { CMD_CLOSE
, "Request Closure" },
87 { CMD_GET_STATUS
, "Get Printer Status" },
88 { CMD_PRINT
, "Print" },
89 { CMD_GET_ID
, "Get Printer Identity" },
90 { CMD_SCAN_JOB
, "Scan Job Details" },
94 static int dissect_bjnp (tvbuff_t
*tvb
, packet_info
*pinfo
, proto_tree
*tree
, void *data _U_
)
96 proto_tree
*bjnp_tree
;
100 guint8 dev_type
, cmd_code
;
103 /* If it does not start with a printable character it's not BJNP */
104 if(!isprint(tvb_get_guint8(tvb
, 0)))
107 col_set_str (pinfo
->cinfo
, COL_PROTOCOL
, PSNAME
);
108 col_clear (pinfo
->cinfo
, COL_INFO
);
110 ti
= proto_tree_add_item (tree
, proto_bjnp
, tvb
, offset
, -1, ENC_NA
);
111 bjnp_tree
= proto_item_add_subtree (ti
, ett_bjnp
);
113 proto_tree_add_item (bjnp_tree
, hf_bjnp_id
, tvb
, offset
, 4, ENC_ASCII
|ENC_NA
);
116 dev_type
= tvb_get_guint8 (tvb
, offset
);
117 proto_tree_add_item (bjnp_tree
, hf_dev_type
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
120 cmd_code
= tvb_get_guint8 (tvb
, offset
);
121 proto_tree_add_item (bjnp_tree
, hf_cmd_code
, tvb
, offset
, 1, ENC_BIG_ENDIAN
);
124 info
= wmem_strdup_printf(wmem_packet_scope(), "%s: %s",
125 val_to_str (dev_type
, dev_type_vals
, "Unknown type (%d)"),
126 val_to_str (cmd_code
, cmd_code_vals
, "Unknown code (%d)"));
128 proto_item_append_text (ti
, ", %s", info
);
129 col_add_str (pinfo
->cinfo
, COL_INFO
, info
);
131 proto_tree_add_item (bjnp_tree
, hf_seq_no
, tvb
, offset
, 4, ENC_BIG_ENDIAN
);
134 proto_tree_add_item (bjnp_tree
, hf_session_id
, tvb
, offset
, 2, ENC_BIG_ENDIAN
);
137 payload_len
= tvb_get_ntohl (tvb
, offset
);
138 proto_tree_add_item (bjnp_tree
, hf_payload_len
, tvb
, offset
, 4, ENC_BIG_ENDIAN
);
141 if (payload_len
> 0) {
142 /* TBD: Dissect various commands */
143 proto_tree_add_item (bjnp_tree
, hf_payload
, tvb
, offset
, payload_len
, ENC_NA
);
144 offset
+= payload_len
;
149 void proto_register_bjnp (void)
151 static hf_register_info hf
[] = {
153 { "Id", "bjnp.id", FT_STRING
, BASE_NONE
,
154 NULL
, 0x0, NULL
, HFILL
} },
156 { "Type", "bjnp.type", FT_UINT8
, BASE_DEC
,
157 VALS(dev_type_vals
), 0x0, NULL
, HFILL
} },
159 { "Code", "bjnp.code", FT_UINT8
, BASE_DEC
,
160 VALS(cmd_code_vals
), 0x0, NULL
, HFILL
} },
162 { "Sequence Number", "bjnp.seq_no", FT_UINT32
, BASE_DEC
,
163 NULL
, 0x0, NULL
, HFILL
} },
165 { "Session Id", "bjnp.session_id", FT_UINT16
, BASE_DEC
,
166 NULL
, 0x0, NULL
, HFILL
} },
168 { "Payload Length", "bjnp.payload_len", FT_UINT32
, BASE_DEC
,
169 NULL
, 0x0, NULL
, HFILL
} },
171 { "Payload", "bjnp.payload", FT_BYTES
, BASE_NONE
,
172 NULL
, 0x0, NULL
, HFILL
} },
175 static gint
*ett
[] = {
179 proto_bjnp
= proto_register_protocol (PNAME
, PSNAME
, PFNAME
);
181 bjnp_handle
= new_register_dissector (PFNAME
, dissect_bjnp
, proto_bjnp
);
183 proto_register_field_array (proto_bjnp
, hf
, array_length (hf
));
184 proto_register_subtree_array (ett
, array_length (ett
));
187 void proto_reg_handoff_bjnp (void)
189 dissector_add_uint ("udp.port", BJNP_PORT1
, bjnp_handle
);
190 dissector_add_uint ("udp.port", BJNP_PORT2
, bjnp_handle
);
191 dissector_add_uint ("udp.port", BJNP_PORT3
, bjnp_handle
);
192 dissector_add_uint ("udp.port", BJNP_PORT4
, bjnp_handle
);
201 * indent-tabs-mode: nil
204 * ex: set shiftwidth=2 tabstop=8 expandtab:
205 * :indentSize=2:tabSize=8:noTabs=true: