/src/wireshark/epan/dissectors/packet-gearman.c
Line | Count | Source |
1 | | /* packet-gearman.c |
2 | | * Routines for Gearman protocol packet disassembly |
3 | | * By Flier Lu <flier.lu@gmail.com> |
4 | | * Copyright 2010 Flier Lu |
5 | | * |
6 | | * Gearman Protocol |
7 | | * ---------------- |
8 | | * http://gearman.org/protocol/ |
9 | | * |
10 | | * Wireshark - Network traffic analyzer |
11 | | * By Gerald Combs <gerald@wireshark.org> |
12 | | * Copyright 1998 Gerald Combs |
13 | | * |
14 | | * SPDX-License-Identifier: GPL-2.0-or-later |
15 | | */ |
16 | | |
17 | | #include "config.h" |
18 | | |
19 | | #include <epan/packet.h> |
20 | | #include <epan/prefs.h> |
21 | | #include <epan/expert.h> |
22 | | #include <wsutil/array.h> |
23 | | #include "packet-tcp.h" |
24 | | |
25 | | void proto_register_gearman(void); |
26 | | void proto_reg_handoff_gearman(void); |
27 | | |
28 | | static dissector_handle_t gearman_handle; |
29 | | |
30 | | static int proto_gearman; |
31 | | |
32 | | static int hf_gearman_mgr_cmd; |
33 | | static int hf_gearman_magic_code; |
34 | | static int hf_gearman_pkt_type; |
35 | | static int hf_gearman_data_size; |
36 | | static int hf_gearman_data_content; |
37 | | static int hf_gearman_option_name; |
38 | | static int hf_gearman_func_name; |
39 | | static int hf_gearman_func_namez; |
40 | | static int hf_gearman_client_id; |
41 | | static int hf_gearman_client_count; |
42 | | static int hf_gearman_uniq_id; |
43 | | static int hf_gearman_uniq_idz; |
44 | | static int hf_gearman_argument; |
45 | | static int hf_gearman_job_handle; |
46 | | static int hf_gearman_job_handlez; |
47 | | static int hf_gearman_complete_numerator; |
48 | | static int hf_gearman_complete_denominator; |
49 | | static int hf_gearman_submit_job_sched_minute; |
50 | | static int hf_gearman_submit_job_sched_hour; |
51 | | static int hf_gearman_submit_job_sched_day_of_month; |
52 | | static int hf_gearman_submit_job_sched_month; |
53 | | static int hf_gearman_submit_job_sched_day_of_week; |
54 | | static int hf_gearman_submit_job_epoch_time; |
55 | | static int hf_gearman_reducer; |
56 | | static int hf_gearman_result; |
57 | | static int hf_gearman_known_status; |
58 | | static int hf_gearman_running_status; |
59 | | static int hf_gearman_timeout_value; |
60 | | static int hf_gearman_echo_text; |
61 | | static int hf_gearman_err_code; |
62 | | static int hf_gearman_err_text; |
63 | | |
64 | | static int ett_gearman; |
65 | | static int ett_gearman_command; |
66 | | static int ett_gearman_content; |
67 | | |
68 | | static expert_field ei_gearman_pkt_type_unknown; |
69 | | |
70 | | static bool gearman_desegment = true; |
71 | | |
72 | | static const int GEARMAN_COMMAND_HEADER_SIZE = 12; |
73 | | static const int GEARMAN_PORT = 4730; |
74 | | static const unsigned char *GEARMAN_MAGIC_CODE_REQUEST = (uint8_t*)"\0REQ"; |
75 | | static const unsigned char *GEARMAN_MAGIC_CODE_RESPONSE = (uint8_t*)"\0RES"; |
76 | | |
77 | | static const char *GEARMAN_MGR_CMDS[] = { |
78 | | "workers", |
79 | | "status", |
80 | | "maxqueue", |
81 | | "shutdown", |
82 | | "version" |
83 | | }; |
84 | | |
85 | | static const unsigned GEARMAN_MGR_CMDS_COUNT = array_length(GEARMAN_MGR_CMDS); |
86 | | |
87 | | typedef enum |
88 | | { |
89 | | GEARMAN_COMMAND_TEXT, |
90 | | GEARMAN_COMMAND_CAN_DO, /* W->J: FUNC */ |
91 | | GEARMAN_COMMAND_CANT_DO, /* W->J: FUNC */ |
92 | | GEARMAN_COMMAND_RESET_ABILITIES, /* W->J: -- */ |
93 | | GEARMAN_COMMAND_PRE_SLEEP, /* W->J: -- */ |
94 | | GEARMAN_COMMAND_UNUSED, |
95 | | GEARMAN_COMMAND_NOOP, /* J->W: -- */ |
96 | | GEARMAN_COMMAND_SUBMIT_JOB, /* C->J: FUNC[0]UNIQ[0]ARGS */ |
97 | | GEARMAN_COMMAND_JOB_CREATED, /* J->C: HANDLE */ |
98 | | GEARMAN_COMMAND_GRAB_JOB, /* W->J: -- */ |
99 | | GEARMAN_COMMAND_NO_JOB, /* J->W: -- */ |
100 | | GEARMAN_COMMAND_JOB_ASSIGN, /* J->W: HANDLE[0]FUNC[0]ARG */ |
101 | | GEARMAN_COMMAND_WORK_STATUS, /* W->J/C: HANDLE[0]NUMERATOR[0]DENOMINATOR */ |
102 | | GEARMAN_COMMAND_WORK_COMPLETE, /* W->J/C: HANDLE[0]RES */ |
103 | | GEARMAN_COMMAND_WORK_FAIL, /* W->J/C: HANDLE */ |
104 | | GEARMAN_COMMAND_GET_STATUS, /* C->J: HANDLE */ |
105 | | GEARMAN_COMMAND_ECHO_REQ, /* ?->J: TEXT */ |
106 | | GEARMAN_COMMAND_ECHO_RES, /* J->?: TEXT */ |
107 | | GEARMAN_COMMAND_SUBMIT_JOB_BG, /* C->J: FUNC[0]UNIQ[0]ARGS */ |
108 | | GEARMAN_COMMAND_ERROR, /* J->?: ERRCODE[0]ERR_TEXT */ |
109 | | GEARMAN_COMMAND_STATUS_RES, /* C->J: HANDLE[0]KNOWN[0]RUNNING[0]NUM[0]DENOM */ |
110 | | GEARMAN_COMMAND_SUBMIT_JOB_HIGH, /* C->J: FUNC[0]UNIQ[0]ARGS */ |
111 | | GEARMAN_COMMAND_SET_CLIENT_ID, /* W->J: [RANDOM_STRING_NO_WHITESPACE] */ |
112 | | GEARMAN_COMMAND_CAN_DO_TIMEOUT, /* W->J: FUNC[0]TIMEOUT */ |
113 | | GEARMAN_COMMAND_ALL_YOURS, |
114 | | GEARMAN_COMMAND_WORK_EXCEPTION, |
115 | | GEARMAN_COMMAND_OPTION_REQ, |
116 | | GEARMAN_COMMAND_OPTION_RES, |
117 | | GEARMAN_COMMAND_WORK_DATA, |
118 | | GEARMAN_COMMAND_WORK_WARNING, |
119 | | GEARMAN_COMMAND_GRAB_JOB_UNIQ, |
120 | | GEARMAN_COMMAND_JOB_ASSIGN_UNIQ, |
121 | | GEARMAN_COMMAND_SUBMIT_JOB_HIGH_BG, |
122 | | GEARMAN_COMMAND_SUBMIT_JOB_LOW, |
123 | | GEARMAN_COMMAND_SUBMIT_JOB_LOW_BG, |
124 | | GEARMAN_COMMAND_SUBMIT_JOB_SCHED, |
125 | | GEARMAN_COMMAND_SUBMIT_JOB_EPOCH, |
126 | | GEARMAN_COMMAND_SUBMIT_REDUCE_JOB, /* C->J: FUNC[0]UNIQ[0]REDUCER[0]UNUSED[0]ARGS */ |
127 | | GEARMAN_COMMAND_SUBMIT_REDUCE_JOB_BG, /* C->J: FUNC[0]UNIQ[0]REDUCER[0]UNUSED[0]ARGS */ |
128 | | GEARMAN_COMMAND_GRAB_JOB_ALL, /* W->J -- */ |
129 | | GEARMAN_COMMAND_JOB_ASSIGN_ALL, /* J->W: HANDLE[0]FUNC[0]UNIQ[0]REDUCER[0]ARGS */ |
130 | | GEARMAN_COMMAND_GET_STATUS_UNIQUE, /* C->J: UNIQUE */ |
131 | | GEARMAN_COMMAND_STATUS_RES_UNIQUE, /* J->C: UNIQUE[0]KNOWN[0]RUNNING[0]NUM[0]DENOM[0]CLIENT_COUNT */ |
132 | | GEARMAN_COMMAND_MAX /* Always add new commands before this. */ |
133 | | } gearman_command_t; |
134 | | |
135 | | static const value_string gearman_command_names[] = { |
136 | | { GEARMAN_COMMAND_TEXT, "TEXT" }, |
137 | | { GEARMAN_COMMAND_CAN_DO, "CAN_DO" }, /* W->J: FUNC */ |
138 | | { GEARMAN_COMMAND_CANT_DO, "CANT_DO" }, /* W->J: FUNC */ |
139 | | { GEARMAN_COMMAND_RESET_ABILITIES, "RESET_ABILITIES" }, /* W->J: -- */ |
140 | | { GEARMAN_COMMAND_PRE_SLEEP, "PRE_SLEEP" }, /* W->J: -- */ |
141 | | { GEARMAN_COMMAND_UNUSED, "UNUSED" }, |
142 | | { GEARMAN_COMMAND_NOOP, "NOOP" }, /* J->W: -- */ |
143 | | { GEARMAN_COMMAND_SUBMIT_JOB, "SUBMIT_JOB" }, /* C->J: FUNC[0]UNIQ[0]ARGS */ |
144 | | { GEARMAN_COMMAND_JOB_CREATED, "JOB_CREATED" }, /* J->C: HANDLE */ |
145 | | { GEARMAN_COMMAND_GRAB_JOB, "GRAB_JOB" }, /* W->J: -- */ |
146 | | { GEARMAN_COMMAND_NO_JOB, "NO_JOB" }, /* J->W: -- */ |
147 | | { GEARMAN_COMMAND_JOB_ASSIGN, "JOB_ASSIGN" }, /* J->W: HANDLE[0]FUNC[0]ARG */ |
148 | | { GEARMAN_COMMAND_WORK_STATUS, "WORK_STATUS" }, /* W->J/C: HANDLE[0]NUMERATOR[0]DENOMINATOR */ |
149 | | { GEARMAN_COMMAND_WORK_COMPLETE, "WORK_COMPLETE" }, /* W->J/C: HANDLE[0]RES */ |
150 | | { GEARMAN_COMMAND_WORK_FAIL, "WORK_FAIL" }, /* W->J/C: HANDLE */ |
151 | | { GEARMAN_COMMAND_GET_STATUS, "GET_STATUS" }, /* C->J: HANDLE */ |
152 | | { GEARMAN_COMMAND_ECHO_REQ, "ECHO_REQ" }, /* ?->J: TEXT */ |
153 | | { GEARMAN_COMMAND_ECHO_RES, "ECHO_RES" }, /* J->?: TEXT */ |
154 | | { GEARMAN_COMMAND_SUBMIT_JOB_BG, "SUBMIT_JOB_BG" }, /* C->J: FUNC[0]UNIQ[0]ARGS */ |
155 | | { GEARMAN_COMMAND_ERROR, "ERROR" }, /* J->?: ERRCODE[0]ERR_TEXT */ |
156 | | { GEARMAN_COMMAND_STATUS_RES, "STATUS_RES" }, /* C->J: HANDLE[0]KNOWN[0]RUNNING[0]NUM[0]DENOM */ |
157 | | { GEARMAN_COMMAND_SUBMIT_JOB_HIGH, "SUBMIT_JOB_HIGH" }, /* C->J: FUNC[0]UNIQ[0]ARGS */ |
158 | | { GEARMAN_COMMAND_SET_CLIENT_ID, "SET_CLIENT_ID" }, /* W->J: [RANDOM_STRING_NO_WHITESPACE] */ |
159 | | { GEARMAN_COMMAND_CAN_DO_TIMEOUT, "CAN_DO_TIMEOUT" }, /* W->J: FUNC[0]TIMEOUT */ |
160 | | { GEARMAN_COMMAND_ALL_YOURS, "ALL_YOURS" }, |
161 | | { GEARMAN_COMMAND_WORK_EXCEPTION, "WORK_EXCEPTION" }, |
162 | | { GEARMAN_COMMAND_OPTION_REQ, "OPTION_REQ" }, |
163 | | { GEARMAN_COMMAND_OPTION_RES, "OPTION_RES" }, |
164 | | { GEARMAN_COMMAND_WORK_DATA, "WORK_DATA" }, |
165 | | { GEARMAN_COMMAND_WORK_WARNING, "WORK_WARNING" }, |
166 | | { GEARMAN_COMMAND_GRAB_JOB_UNIQ, "GRAB_JOB_UNIQ" }, |
167 | | { GEARMAN_COMMAND_JOB_ASSIGN_UNIQ, "JOB_ASSIGN_UNIQ" }, |
168 | | { GEARMAN_COMMAND_SUBMIT_JOB_HIGH_BG, "SUBMIT_JOB_HIGH_BG" }, |
169 | | { GEARMAN_COMMAND_SUBMIT_JOB_LOW, "SUBMIT_JOB_LOW" }, |
170 | | { GEARMAN_COMMAND_SUBMIT_JOB_LOW_BG, "SUBMIT_JOB_LOW_BG" }, |
171 | | { GEARMAN_COMMAND_SUBMIT_JOB_SCHED, "SUBMIT_JOB_SCHED" }, |
172 | | { GEARMAN_COMMAND_SUBMIT_JOB_EPOCH, "SUBMIT_JOB_EPOCH" }, |
173 | | { GEARMAN_COMMAND_SUBMIT_REDUCE_JOB, "SUBMIT_REDUCE_JOB" }, |
174 | | { GEARMAN_COMMAND_SUBMIT_REDUCE_JOB_BG, "SUBMIT_REDUCE_JOB_BG" }, |
175 | | { GEARMAN_COMMAND_GRAB_JOB_ALL, "GRAB_JOB_ALL" }, |
176 | | { GEARMAN_COMMAND_JOB_ASSIGN_ALL, "JOB_ASSIGN_ALL" }, |
177 | | { GEARMAN_COMMAND_GET_STATUS_UNIQUE, "GET_STATUS_UNIQUE" }, |
178 | | { GEARMAN_COMMAND_STATUS_RES_UNIQUE, "STATUS_RES_UNIQUE" }, |
179 | | { 0, NULL} |
180 | | }; |
181 | | |
182 | | static unsigned |
183 | | get_gearman_pdu_len(packet_info *pinfo _U_, tvbuff_t *tvb, int offset, void *data _U_) |
184 | 2 | { |
185 | 2 | return tvb_get_ntohl(tvb, offset+8)+GEARMAN_COMMAND_HEADER_SIZE; |
186 | 2 | } |
187 | | |
188 | | static int |
189 | | dissect_binary_packet(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data _U_) |
190 | 2 | { |
191 | 2 | unsigned curr_offset; |
192 | 2 | char *magic_code; |
193 | 2 | uint32_t type, size; |
194 | 2 | unsigned len; |
195 | 2 | proto_item *content_item = NULL; |
196 | 2 | proto_tree *content_tree = NULL; |
197 | | |
198 | 2 | col_set_str(pinfo->cinfo, COL_PROTOCOL, "Gearman"); |
199 | 2 | col_clear(pinfo->cinfo,COL_INFO); |
200 | | |
201 | 2 | magic_code = (char*)tvb_get_string_enc(pinfo->pool, tvb, 1, 3, ENC_ASCII); |
202 | 2 | type = tvb_get_ntohl(tvb, 4); |
203 | 2 | size = tvb_get_ntohl(tvb, 8); |
204 | | |
205 | 2 | col_append_sep_fstr(pinfo->cinfo, COL_INFO, " , ", "[%s] ", magic_code); |
206 | | |
207 | 2 | col_append_fstr(pinfo->cinfo, COL_INFO, "%s(%d) LEN=%d", |
208 | 2 | val_to_str(pinfo->pool, type, gearman_command_names, "Unknown (0x%08x)"), type, size); |
209 | | |
210 | 2 | if (tree) { |
211 | 2 | proto_item *ti; |
212 | 2 | proto_tree *command_tree, *gearman_tree; |
213 | 2 | ti = proto_tree_add_item(tree, proto_gearman, tvb, 0, -1, ENC_NA); |
214 | 2 | gearman_tree = proto_item_add_subtree(ti, ett_gearman); |
215 | | |
216 | 2 | command_tree = proto_tree_add_subtree_format(gearman_tree, tvb, 0, GEARMAN_COMMAND_HEADER_SIZE+size, ett_gearman_command, NULL, |
217 | 2 | "[%s] %s(%d) LEN=%d", magic_code, val_to_str(pinfo->pool, type, gearman_command_names, "Unknown (0x%08x)"), type, size); |
218 | | |
219 | 2 | proto_tree_add_string(command_tree, hf_gearman_magic_code, tvb, 0, 4, magic_code); |
220 | 2 | proto_tree_add_item(command_tree, hf_gearman_pkt_type, tvb, 4, 4, ENC_BIG_ENDIAN); |
221 | 2 | proto_tree_add_item(command_tree, hf_gearman_data_size, tvb, 8, 4, ENC_BIG_ENDIAN); |
222 | | |
223 | | // explicitly set len to 0 if there are no arguments, |
224 | | // else use tvb_strnlen() to find the remaining length of tvb |
225 | 2 | len = ( size > 0 ) ? tvb_strnlen( tvb, GEARMAN_COMMAND_HEADER_SIZE, -1 ) : 0 ; |
226 | 2 | content_item = proto_tree_add_item(command_tree, hf_gearman_data_content, tvb, GEARMAN_COMMAND_HEADER_SIZE, len, ENC_ASCII); |
227 | 2 | content_tree = proto_item_add_subtree(content_item, ett_gearman_content); |
228 | 2 | } |
229 | | |
230 | 2 | curr_offset = GEARMAN_COMMAND_HEADER_SIZE; |
231 | | |
232 | 2 | switch(type) |
233 | 2 | { |
234 | | |
235 | | // |
236 | | // when determining len for proto_tree_add_item() |
237 | | // |
238 | | // if the command has one argument: |
239 | | // - use tvb_strnlen() |
240 | | // |
241 | | // if the command has multiple arguments: |
242 | | // - use tvb_strsize() for the all but the last argument |
243 | | // - use tvb_strnlen() for the last argument |
244 | | // |
245 | | // These are *not* null-terminated strings, they're null-separated |
246 | | // strings. For example, some arguments might be the last argument |
247 | | // in some commands and not be the last argument in other commands, |
248 | | // so they're not always followed by a null. |
249 | | |
250 | | // |
251 | | // commands with a single argument |
252 | | // |
253 | | |
254 | 0 | case GEARMAN_COMMAND_ECHO_REQ: |
255 | 0 | case GEARMAN_COMMAND_ECHO_RES: |
256 | 0 | if (!tree) break; |
257 | 0 | if (tvb_captured_length_remaining(tvb, curr_offset) == 0) break; |
258 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
259 | 0 | proto_tree_add_item(content_tree, hf_gearman_echo_text, tvb, curr_offset, len, ENC_ASCII); |
260 | 0 | break; |
261 | | |
262 | 0 | case GEARMAN_COMMAND_JOB_CREATED: |
263 | 0 | case GEARMAN_COMMAND_WORK_FAIL: |
264 | 0 | if (!tree) break; |
265 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
266 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handle, tvb, curr_offset, len, ENC_ASCII); |
267 | 0 | break; |
268 | | |
269 | 0 | case GEARMAN_COMMAND_OPTION_REQ: |
270 | 0 | case GEARMAN_COMMAND_OPTION_RES: |
271 | 0 | if (!tree) break; |
272 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
273 | 0 | proto_tree_add_item(content_tree, hf_gearman_option_name, tvb, curr_offset, len, ENC_ASCII); |
274 | 0 | break; |
275 | | |
276 | 0 | case GEARMAN_COMMAND_SET_CLIENT_ID: |
277 | 0 | if (!tree) break; |
278 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
279 | 0 | proto_tree_add_item(content_tree, hf_gearman_client_id, tvb, curr_offset, len, ENC_ASCII); |
280 | 0 | break; |
281 | | |
282 | 0 | case GEARMAN_COMMAND_GET_STATUS_UNIQUE: |
283 | 0 | if (!tree) break; |
284 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
285 | 0 | proto_tree_add_item(content_tree, hf_gearman_uniq_id, tvb, curr_offset, len, ENC_ASCII); |
286 | 0 | break; |
287 | | |
288 | 0 | case GEARMAN_COMMAND_CAN_DO: |
289 | 0 | case GEARMAN_COMMAND_CANT_DO: |
290 | 0 | if (!tree) break; |
291 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
292 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_name, tvb, curr_offset, len, ENC_ASCII); |
293 | 0 | break; |
294 | | |
295 | | // |
296 | | // commands with multiple arguments |
297 | | // |
298 | | |
299 | 0 | case GEARMAN_COMMAND_ERROR: |
300 | 0 | if (!tree) break; |
301 | 0 | len = tvb_strsize(tvb, curr_offset); |
302 | 0 | proto_tree_add_item(content_tree, hf_gearman_err_code, tvb, curr_offset, len, ENC_ASCII); |
303 | |
|
304 | 0 | curr_offset += len; |
305 | 0 | if (tvb_captured_length_remaining(tvb, curr_offset) == 0) break; |
306 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
307 | 0 | proto_tree_add_item(content_tree, hf_gearman_err_text, tvb, curr_offset, len, ENC_ASCII); |
308 | 0 | break; |
309 | | |
310 | 0 | case GEARMAN_COMMAND_WORK_DATA: |
311 | 0 | case GEARMAN_COMMAND_WORK_WARNING: |
312 | 0 | case GEARMAN_COMMAND_WORK_COMPLETE: |
313 | 0 | case GEARMAN_COMMAND_WORK_EXCEPTION: |
314 | 0 | if (!tree) break; |
315 | 0 | len = tvb_strsize(tvb, curr_offset); |
316 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handlez, tvb, curr_offset, len, ENC_ASCII); |
317 | |
|
318 | 0 | curr_offset += len; |
319 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
320 | 0 | proto_tree_add_item(content_tree, hf_gearman_result, tvb, curr_offset, len, ENC_ASCII); |
321 | 0 | break; |
322 | | |
323 | 0 | case GEARMAN_COMMAND_STATUS_RES: |
324 | 0 | if (!tree) break; |
325 | 0 | len = tvb_strsize(tvb, curr_offset); |
326 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handlez, tvb, curr_offset, len, ENC_ASCII); |
327 | |
|
328 | 0 | curr_offset += len; |
329 | 0 | len = tvb_strsize(tvb, curr_offset); |
330 | 0 | proto_tree_add_item(content_tree, hf_gearman_known_status, tvb, curr_offset, len, ENC_ASCII); |
331 | |
|
332 | 0 | curr_offset += len; |
333 | 0 | len = tvb_strsize(tvb, curr_offset); |
334 | 0 | proto_tree_add_item(content_tree, hf_gearman_running_status, tvb, curr_offset, len, ENC_ASCII); |
335 | |
|
336 | 0 | curr_offset += len; |
337 | 0 | len = tvb_strsize(tvb, curr_offset); |
338 | 0 | proto_tree_add_item(content_tree, hf_gearman_complete_numerator, tvb, curr_offset, len, ENC_ASCII); |
339 | |
|
340 | 0 | curr_offset += len; |
341 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
342 | 0 | proto_tree_add_item(content_tree, hf_gearman_complete_denominator, tvb, curr_offset, len, ENC_ASCII); |
343 | 0 | break; |
344 | | |
345 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB: |
346 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB_BG: |
347 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB_HIGH: |
348 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB_HIGH_BG: |
349 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB_LOW: |
350 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB_LOW_BG: |
351 | 0 | if (!tree) break; |
352 | 0 | len = tvb_strsize(tvb, curr_offset); |
353 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
354 | |
|
355 | 0 | curr_offset += len; |
356 | 0 | len = tvb_strsize(tvb, curr_offset); |
357 | 0 | proto_tree_add_item(content_tree, hf_gearman_uniq_idz, tvb, curr_offset, len, ENC_ASCII); |
358 | |
|
359 | 0 | curr_offset += len; |
360 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
361 | 0 | proto_tree_add_item(content_tree, hf_gearman_argument, tvb, curr_offset, len, ENC_ASCII); |
362 | 0 | break; |
363 | | |
364 | 0 | case GEARMAN_COMMAND_SUBMIT_REDUCE_JOB: |
365 | 0 | case GEARMAN_COMMAND_SUBMIT_REDUCE_JOB_BG: |
366 | 0 | if (!tree) break; |
367 | 0 | len = tvb_strsize(tvb, curr_offset); |
368 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
369 | |
|
370 | 0 | curr_offset += len; |
371 | 0 | len = tvb_strsize(tvb, curr_offset); |
372 | 0 | proto_tree_add_item(content_tree, hf_gearman_uniq_idz, tvb, curr_offset, len, ENC_ASCII); |
373 | |
|
374 | 0 | curr_offset += len; |
375 | 0 | len = tvb_strsize(tvb, curr_offset); |
376 | 0 | proto_tree_add_item(content_tree, hf_gearman_reducer, tvb, curr_offset, len, ENC_ASCII); |
377 | |
|
378 | 0 | curr_offset += len; |
379 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
380 | 0 | proto_tree_add_item(content_tree, hf_gearman_argument, tvb, curr_offset, len, ENC_ASCII); |
381 | 0 | break; |
382 | | |
383 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB_SCHED: |
384 | 0 | if (!tree) break; |
385 | 0 | len = tvb_strsize(tvb, curr_offset); |
386 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
387 | |
|
388 | 0 | curr_offset += len; |
389 | 0 | len = tvb_strsize(tvb, curr_offset); |
390 | 0 | proto_tree_add_item(content_tree, hf_gearman_uniq_idz, tvb, curr_offset, len, ENC_ASCII); |
391 | |
|
392 | 0 | curr_offset += len; |
393 | 0 | len = tvb_strsize(tvb, curr_offset); |
394 | 0 | proto_tree_add_item(content_tree, hf_gearman_submit_job_sched_minute, tvb, curr_offset, len, ENC_ASCII); |
395 | |
|
396 | 0 | curr_offset += len; |
397 | 0 | len = tvb_strsize(tvb, curr_offset); |
398 | 0 | proto_tree_add_item(content_tree, hf_gearman_submit_job_sched_hour, tvb, curr_offset, len, ENC_ASCII); |
399 | |
|
400 | 0 | curr_offset += len; |
401 | 0 | len = tvb_strsize(tvb, curr_offset); |
402 | 0 | proto_tree_add_item(content_tree, hf_gearman_submit_job_sched_day_of_month, tvb, curr_offset, len, ENC_ASCII); |
403 | |
|
404 | 0 | curr_offset += len; |
405 | 0 | len = tvb_strsize(tvb, curr_offset); |
406 | 0 | proto_tree_add_item(content_tree, hf_gearman_submit_job_sched_month, tvb, curr_offset, len, ENC_ASCII); |
407 | |
|
408 | 0 | curr_offset += len; |
409 | 0 | len = tvb_strsize(tvb, curr_offset); |
410 | 0 | proto_tree_add_item(content_tree, hf_gearman_submit_job_sched_day_of_week, tvb, curr_offset, len, ENC_ASCII); |
411 | |
|
412 | 0 | curr_offset += len; |
413 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
414 | 0 | proto_tree_add_item(content_tree, hf_gearman_argument, tvb, curr_offset, len, ENC_ASCII); |
415 | 0 | break; |
416 | | |
417 | 0 | case GEARMAN_COMMAND_SUBMIT_JOB_EPOCH: |
418 | 0 | if (!tree) break; |
419 | 0 | len = tvb_strsize(tvb, curr_offset); |
420 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
421 | |
|
422 | 0 | curr_offset += len; |
423 | 0 | len = tvb_strsize(tvb, curr_offset); |
424 | 0 | proto_tree_add_item(content_tree, hf_gearman_uniq_idz, tvb, curr_offset, len, ENC_ASCII); |
425 | |
|
426 | 0 | curr_offset += len; |
427 | 0 | len = tvb_strsize(tvb, curr_offset); |
428 | 0 | proto_tree_add_item(content_tree, hf_gearman_submit_job_epoch_time, tvb, curr_offset, len, ENC_ASCII); |
429 | |
|
430 | 0 | curr_offset += len; |
431 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
432 | 0 | proto_tree_add_item(content_tree, hf_gearman_argument, tvb, curr_offset, len, ENC_ASCII); |
433 | 0 | break; |
434 | | |
435 | 0 | case GEARMAN_COMMAND_JOB_ASSIGN: |
436 | 0 | len = tvb_strsize(tvb, curr_offset); |
437 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handlez, tvb, curr_offset, len, ENC_ASCII); |
438 | |
|
439 | 0 | curr_offset += len; |
440 | 0 | len = tvb_strsize(tvb, curr_offset); |
441 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
442 | |
|
443 | 0 | curr_offset += len; |
444 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
445 | 0 | proto_tree_add_item(content_tree, hf_gearman_argument, tvb, curr_offset, len, ENC_ASCII); |
446 | 0 | break; |
447 | | |
448 | 0 | case GEARMAN_COMMAND_JOB_ASSIGN_UNIQ: |
449 | 0 | len = tvb_strsize(tvb, curr_offset); |
450 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handlez, tvb, curr_offset, len, ENC_ASCII); |
451 | |
|
452 | 0 | curr_offset += len; |
453 | 0 | len = tvb_strsize(tvb, curr_offset); |
454 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
455 | |
|
456 | 0 | curr_offset += len; |
457 | 0 | len = tvb_strsize(tvb, curr_offset); |
458 | 0 | proto_tree_add_item(content_tree, hf_gearman_uniq_idz, tvb, curr_offset, len, ENC_ASCII); |
459 | |
|
460 | 0 | curr_offset += len; |
461 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
462 | 0 | proto_tree_add_item(content_tree, hf_gearman_argument, tvb, curr_offset, len, ENC_ASCII); |
463 | 0 | break; |
464 | | |
465 | 0 | case GEARMAN_COMMAND_JOB_ASSIGN_ALL: |
466 | 0 | if (!tree) break; |
467 | 0 | len = tvb_strsize(tvb, curr_offset); |
468 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handlez, tvb, curr_offset, len, ENC_ASCII); |
469 | |
|
470 | 0 | curr_offset += len; |
471 | 0 | len = tvb_strsize(tvb, curr_offset); |
472 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
473 | |
|
474 | 0 | curr_offset += len; |
475 | 0 | len = tvb_strsize(tvb, curr_offset); |
476 | 0 | proto_tree_add_item(content_tree, hf_gearman_uniq_idz, tvb, curr_offset, len, ENC_ASCII); |
477 | |
|
478 | 0 | curr_offset += len; |
479 | 0 | len = tvb_strsize(tvb, curr_offset); |
480 | 0 | proto_tree_add_item(content_tree, hf_gearman_reducer, tvb, curr_offset, len, ENC_ASCII); |
481 | |
|
482 | 0 | curr_offset += len; |
483 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
484 | 0 | proto_tree_add_item(content_tree, hf_gearman_argument, tvb, curr_offset, len, ENC_ASCII); |
485 | 0 | break; |
486 | | |
487 | 0 | case GEARMAN_COMMAND_WORK_STATUS: |
488 | 0 | if (!tree) break; |
489 | 0 | len = tvb_strsize(tvb, curr_offset); |
490 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handlez, tvb, curr_offset, len, ENC_ASCII); |
491 | |
|
492 | 0 | curr_offset += len; |
493 | 0 | len = tvb_strsize(tvb, curr_offset); |
494 | 0 | proto_tree_add_item(content_tree, hf_gearman_complete_numerator, tvb, curr_offset, len, ENC_ASCII); |
495 | |
|
496 | 0 | curr_offset += len; |
497 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
498 | 0 | proto_tree_add_item(content_tree, hf_gearman_complete_denominator, tvb, curr_offset, len, ENC_ASCII); |
499 | 0 | break; |
500 | | |
501 | 0 | case GEARMAN_COMMAND_CAN_DO_TIMEOUT: |
502 | 0 | if (!tree) break; |
503 | 0 | len = tvb_strsize(tvb, curr_offset); |
504 | 0 | proto_tree_add_item(content_tree, hf_gearman_func_namez, tvb, curr_offset, len, ENC_ASCII); |
505 | |
|
506 | 0 | curr_offset += len; |
507 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
508 | 0 | proto_tree_add_item(content_tree, hf_gearman_timeout_value, tvb, curr_offset, len, ENC_ASCII); |
509 | 0 | break; |
510 | | |
511 | 0 | case GEARMAN_COMMAND_STATUS_RES_UNIQUE: |
512 | 0 | if (!tree) break; |
513 | 0 | len = tvb_strsize(tvb, curr_offset); |
514 | 0 | proto_tree_add_item(content_tree, hf_gearman_job_handlez, tvb, curr_offset, len, ENC_ASCII); |
515 | |
|
516 | 0 | curr_offset += len; |
517 | 0 | len = tvb_strsize(tvb, curr_offset); |
518 | 0 | proto_tree_add_item(content_tree, hf_gearman_known_status, tvb, curr_offset, len, ENC_ASCII); |
519 | |
|
520 | 0 | curr_offset += len; |
521 | 0 | len = tvb_strsize(tvb, curr_offset); |
522 | 0 | proto_tree_add_item(content_tree, hf_gearman_running_status, tvb, curr_offset, len, ENC_ASCII); |
523 | |
|
524 | 0 | curr_offset += len; |
525 | 0 | len = tvb_strsize(tvb, curr_offset); |
526 | 0 | proto_tree_add_item(content_tree, hf_gearman_complete_numerator, tvb, curr_offset, len, ENC_ASCII); |
527 | |
|
528 | 0 | curr_offset += len; |
529 | 0 | len = tvb_strsize(tvb, curr_offset); |
530 | 0 | proto_tree_add_item(content_tree, hf_gearman_complete_denominator, tvb, curr_offset, len, ENC_ASCII); |
531 | |
|
532 | 0 | curr_offset += len; |
533 | 0 | len = tvb_strnlen( tvb, curr_offset, -1 ); |
534 | 0 | proto_tree_add_item(content_tree, hf_gearman_client_count, tvb, curr_offset, len, ENC_ASCII); |
535 | 0 | break; |
536 | | |
537 | 2 | default: |
538 | 2 | if (size > 0) |
539 | 2 | expert_add_info(pinfo, content_item, &ei_gearman_pkt_type_unknown); |
540 | 2 | } |
541 | | |
542 | 2 | col_set_fence(pinfo->cinfo, COL_INFO); |
543 | 2 | return tvb_captured_length(tvb); |
544 | 2 | } |
545 | | |
546 | | static void |
547 | | dissect_management_packet(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) |
548 | 16 | { |
549 | 16 | unsigned i, type = 0, cmdlen, linelen, offset = 0, next_offset = 0; |
550 | 16 | proto_item *ti; |
551 | 16 | proto_tree *gearman_tree; |
552 | | |
553 | 16 | col_set_str(pinfo->cinfo, COL_PROTOCOL, "Gearman"); |
554 | 16 | col_clear(pinfo->cinfo, COL_INFO); |
555 | | |
556 | 16 | ti = proto_tree_add_item(tree, proto_gearman, tvb, 0, -1, ENC_NA); |
557 | 16 | gearman_tree = proto_item_add_subtree(ti, ett_gearman); |
558 | | |
559 | 113 | while (tvb_find_line_end_remaining(tvb, offset, &linelen, &next_offset)) |
560 | 97 | { |
561 | 582 | for (i=0; i<GEARMAN_MGR_CMDS_COUNT; i++) |
562 | 485 | { |
563 | | /* the array is a const and clearly none of the elements are longer than |
564 | | * MAX_SIGNED_INT so this is a safe cast */ |
565 | 485 | cmdlen = (int)strlen(GEARMAN_MGR_CMDS[i]); |
566 | | |
567 | 485 | if (cmdlen == linelen && 0 == tvb_strneql(tvb, offset, GEARMAN_MGR_CMDS[i], cmdlen)) |
568 | 0 | { |
569 | 0 | const uint8_t* cmdstr; |
570 | 0 | proto_tree_add_item_ret_string(gearman_tree, hf_gearman_mgr_cmd, tvb, offset, cmdlen, ENC_ASCII|ENC_NA, pinfo->pool, &cmdstr); |
571 | 0 | col_add_fstr(pinfo->cinfo, COL_INFO, "[MGR] %s", cmdstr); |
572 | 0 | type = 1; |
573 | 0 | break; |
574 | 0 | } |
575 | 485 | } |
576 | | |
577 | 97 | if (GEARMAN_MGR_CMDS_COUNT == i) |
578 | 97 | { |
579 | 97 | proto_tree_add_format_text(gearman_tree, tvb, offset, next_offset - offset); |
580 | | |
581 | 97 | if (type == 0) |
582 | 15 | { |
583 | 15 | col_add_fstr(pinfo->cinfo, COL_INFO, "[MGR] %s", tvb_get_string_enc(pinfo->pool, tvb, offset, linelen, ENC_ASCII)); |
584 | 15 | type = -1; |
585 | 15 | } |
586 | 82 | else |
587 | 82 | { |
588 | 82 | col_append_sep_str(pinfo->cinfo, COL_INFO, ",", (char*)tvb_get_string_enc(pinfo->pool, tvb, offset, linelen, ENC_ASCII)); |
589 | 82 | } |
590 | 97 | } |
591 | | |
592 | 97 | offset = next_offset; |
593 | 97 | } |
594 | 16 | } |
595 | | |
596 | | static int |
597 | | dissect_gearman(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data) |
598 | 18 | { |
599 | 18 | if ((0 == tvb_memeql(tvb, 0, GEARMAN_MAGIC_CODE_REQUEST, 4)) || |
600 | 18 | (0 == tvb_memeql(tvb, 0, GEARMAN_MAGIC_CODE_RESPONSE, 4))) |
601 | 2 | { |
602 | 2 | tcp_dissect_pdus(tvb, pinfo, tree, gearman_desegment, GEARMAN_COMMAND_HEADER_SIZE, get_gearman_pdu_len, dissect_binary_packet, data); |
603 | 2 | } |
604 | 16 | else |
605 | 16 | { |
606 | 16 | dissect_management_packet(tvb, pinfo, tree); |
607 | 16 | } |
608 | | |
609 | 18 | return tvb_captured_length(tvb); |
610 | 18 | } |
611 | | |
612 | | void |
613 | | proto_register_gearman(void) |
614 | 16 | { |
615 | 16 | static hf_register_info hf[] = { |
616 | 16 | { &hf_gearman_mgr_cmd, { "Management Command", "gearman.mgr_cmd", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL } }, |
617 | 16 | { &hf_gearman_magic_code, { "Magic Code", "gearman.magic_code", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL } }, |
618 | 16 | { &hf_gearman_pkt_type, { "Packet Type", "gearman.pkt_type", FT_UINT32, BASE_DEC_HEX, VALS(gearman_command_names), 0x0, NULL, HFILL} }, |
619 | 16 | { &hf_gearman_data_size, { "Data Length", "gearman.data_size", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL} }, |
620 | 16 | { &hf_gearman_data_content, { "Data Content", "gearman.data_content", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
621 | 16 | { &hf_gearman_option_name, { "Option Name", "gearman.opt.name", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
622 | 16 | { &hf_gearman_func_name, { "Function Name", "gearman.func.name", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
623 | 16 | { &hf_gearman_func_namez, { "Function Name", "gearman.func.name", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
624 | 16 | { &hf_gearman_client_id, { "Client ID", "gearman.client_id", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
625 | 16 | { &hf_gearman_client_count, { "Client Count", "gearman.client_count", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
626 | 16 | { &hf_gearman_uniq_id, { "Unique ID", "gearman.uniq_id", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
627 | 16 | { &hf_gearman_uniq_idz, { "Unique ID", "gearman.uniq_id", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
628 | 16 | { &hf_gearman_argument, { "Function Argument", "gearman.func.arg", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
629 | 16 | { &hf_gearman_job_handle, { "Job Handle", "gearman.job.handle", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
630 | 16 | { &hf_gearman_job_handlez, { "Job Handle", "gearman.job.handle", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
631 | 16 | { &hf_gearman_complete_numerator, { "Complete Numerator", "gearman.numerator", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
632 | 16 | { &hf_gearman_complete_denominator, { "Complete Denominator", "gearman.denominator", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
633 | 16 | { &hf_gearman_submit_job_sched_minute, { "Minute", "gearman.submit_job_sched.minute", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
634 | 16 | { &hf_gearman_submit_job_sched_hour, { "Hour", "gearman.submit_job_sched.hour", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
635 | 16 | { &hf_gearman_submit_job_sched_day_of_month, { "Day of Month", "gearman.submit_job_sched.day_of_month", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
636 | 16 | { &hf_gearman_submit_job_sched_month, { "Month", "gearman.submit_job_sched.month", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
637 | 16 | { &hf_gearman_submit_job_sched_day_of_week, { "Day of Week", "gearman.submit_job_sched.day_of_week", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
638 | 16 | { &hf_gearman_submit_job_epoch_time, { "Epoch Time", "gearman.submit_job.epoch_time", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
639 | 16 | { &hf_gearman_reducer, { "Reducer", "gearman.reducer", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
640 | 16 | { &hf_gearman_result, { "Function Result", "gearman.func.result", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
641 | 16 | { &hf_gearman_known_status, { "Known job", "gearman.job.known", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
642 | 16 | { &hf_gearman_running_status, { "Running Job", "gearman.job.running", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
643 | 16 | { &hf_gearman_timeout_value, { "Timeout Value", "gearman.timeout.value", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
644 | 16 | { &hf_gearman_echo_text, { "Echo Text", "gearman.echo_text", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
645 | 16 | { &hf_gearman_err_code, { "Error Code", "gearman.err.code", FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL} }, |
646 | 16 | { &hf_gearman_err_text, { "Error Text", "gearman.err.text", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL} } |
647 | 16 | }; |
648 | | |
649 | | /* Setup protocol subtree array */ |
650 | 16 | static int *ett[] = { |
651 | 16 | &ett_gearman, |
652 | 16 | &ett_gearman_command, |
653 | 16 | &ett_gearman_content |
654 | 16 | }; |
655 | | |
656 | 16 | static ei_register_info ei[] = { |
657 | 16 | { &ei_gearman_pkt_type_unknown, { "gearman.pkt_type.unknown", PI_PROTOCOL, PI_WARN, "Unknown command", EXPFILL }}, |
658 | 16 | }; |
659 | | |
660 | 16 | module_t *gearman_module; |
661 | 16 | expert_module_t* expert_gearman; |
662 | | |
663 | 16 | proto_gearman = proto_register_protocol("Gearman Protocol", "Gearman", "gearman"); |
664 | | |
665 | 16 | proto_register_field_array(proto_gearman, hf, array_length(hf)); |
666 | 16 | proto_register_subtree_array(ett, array_length(ett)); |
667 | 16 | expert_gearman = expert_register_protocol(proto_gearman); |
668 | 16 | expert_register_field_array(expert_gearman, ei, array_length(ei)); |
669 | | |
670 | 16 | gearman_module = prefs_register_protocol(proto_gearman, NULL); |
671 | 16 | prefs_register_bool_preference(gearman_module, "desegment", |
672 | 16 | "Desegment all Gearman messages spanning multiple TCP segments", |
673 | 16 | "Whether the Gearman dissector should desegment all messages spanning multiple TCP segments", |
674 | 16 | &gearman_desegment); |
675 | | |
676 | 16 | gearman_handle = register_dissector("gearman", dissect_gearman, proto_gearman); |
677 | 16 | } |
678 | | |
679 | | void |
680 | | proto_reg_handoff_gearman(void) |
681 | 16 | { |
682 | 16 | dissector_add_uint_with_preference("tcp.port", GEARMAN_PORT, gearman_handle); |
683 | 16 | } |
684 | | |
685 | | /* |
686 | | * Editor modelines - https://www.wireshark.org/tools/modelines.html |
687 | | * |
688 | | * Local variables: |
689 | | * c-basic-offset: 2 |
690 | | * tab-width: 8 |
691 | | * indent-tabs-mode: nil |
692 | | * End: |
693 | | * |
694 | | * vi: set shiftwidth=2 tabstop=8 expandtab: |
695 | | * :indentSize=2:tabSize=8:noTabs=true: |
696 | | */ |