s4-rpcserver: allow saving of bad RPC packets
authorAndrew Tridgell <tridge@samba.org>
Thu, 16 Sep 2010 07:04:53 +0000 (17:04 +1000)
committerAndrew Tridgell <tridge@samba.org>
Thu, 16 Sep 2010 11:09:17 +0000 (21:09 +1000)
use:
dcesrv:stubs directory = .

to save files like this:

  RPC-netlogon-48-pullfail.dat

when a RPC packet can't be parsed or is unknown. Only enabled in
developer builds

Pair-Programmed-With: Andrew Bartlett <abartlet@samba.org>

source4/rpc_server/dcerpc_server.c

index 09b9b2ac0ab71b890ab76253527117fca834ecee..7bd8dcaa2bde9356d3de5e32ca67c55806265db4 100644 (file)
@@ -943,6 +943,30 @@ static NTSTATUS dcesrv_alter(struct dcesrv_call_state *call)
        return NT_STATUS_OK;
 }
 
+/*
+  possibly save the call for inspection with ndrdump
+ */
+static void dcesrv_save_call(struct dcesrv_call_state *call, const char *why)
+{
+#ifdef DEVELOPER
+       char *fname;
+       char *dump_dir;
+       dump_dir = lpcfg_parm_string(call->conn->dce_ctx->lp_ctx, NULL, "dcesrv", "stubs directory");
+       if (!dump_dir) {
+               return;
+       }
+       fname = talloc_asprintf(call, "%s/RPC-%s-%u-%s.dat",
+                               dump_dir,
+                               call->context->iface->name,
+                               call->pkt.u.request.opnum,
+                               why);
+       if (file_save(fname, call->pkt.u.request.stub_and_verifier.data, call->pkt.u.request.stub_and_verifier.length)) {
+               DEBUG(0,("RPC SAVED %s\n", fname));
+       }
+       talloc_free(fname);
+#endif
+}
+
 /*
   handle a dcerpc request packet
 */
@@ -982,15 +1006,17 @@ static NTSTATUS dcesrv_request(struct dcesrv_call_state *call)
                        /* we got an unknown call */
                        DEBUG(3,(__location__ ": Unknown RPC call %u on %s\n",
                                 call->pkt.u.request.opnum, context->iface->name));
-                       dump_data(3, pull->data, pull->data_size);
+                       dcesrv_save_call(call, "unknown");
+               } else {
+                       dcesrv_save_call(call, "pullfail");
                }
                return dcesrv_fault(call, call->fault_code);
        }
 
        if (pull->offset != pull->data_size) {
+               dcesrv_save_call(call, "extrabytes");
                DEBUG(3,("Warning: %d extra bytes in incoming RPC request\n", 
                         pull->data_size - pull->offset));
-               dump_data(10, pull->data+pull->offset, pull->data_size - pull->offset);
        }
 
        /* call the dispatch function */