diff options
-rw-r--r-- | source3/lib/cmd_interp.c | 6 | ||||
-rw-r--r-- | source3/rpc_client/cli_spoolss.c | 137 | ||||
-rw-r--r-- | source3/rpc_client/msrpc_spoolss.c | 200 | ||||
-rw-r--r-- | source3/rpcclient/cmd_spoolss.c | 91 | ||||
-rw-r--r-- | source3/rpcclient/display_spool.c | 46 | ||||
-rw-r--r-- | source3/rpcclient/spoolss_cmds.c | 9 |
6 files changed, 373 insertions, 116 deletions
diff --git a/source3/lib/cmd_interp.c b/source3/lib/cmd_interp.c index a029d0bbd2..5f7e98c243 100644 --- a/source3/lib/cmd_interp.c +++ b/source3/lib/cmd_interp.c @@ -221,7 +221,7 @@ help ****************************************************************************/ static uint32 cmd_help(struct client_info *info, int argc, char *argv[]) { - int i = 0, j = 0; + int i = 0; /* get help on a specific command */ if (argc > 0) @@ -1159,9 +1159,7 @@ static uint32 cmd_set(struct client_info *info, int argc, char *argv[]) srv_name, usr.ntc.user_name, usr.ntc.domain); report(out_hnd, "Connection:\t"); - if (cli_net_use_add(srv_name, &usr.ntc, info->reuse, - &isnew) - != NULL) + if (cli_net_use_add(srv_name, &usr.ntc, info->reuse, &isnew) != NULL) { report(out_hnd, "OK\n"); } diff --git a/source3/rpc_client/cli_spoolss.c b/source3/rpc_client/cli_spoolss.c index 3e12454cb2..5dda49b4b5 100644 --- a/source3/rpc_client/cli_spoolss.c +++ b/source3/rpc_client/cli_spoolss.c @@ -32,24 +32,23 @@ extern int DEBUGLEVEL; /**************************************************************************** do a SPOOLSS Enum Printer Drivers ****************************************************************************/ -uint32 spoolss_enum_printerdrivers(const char * srv_name, - const char *environment, - uint32 level, - NEW_BUFFER *buffer, uint32 offered, - uint32 *needed, uint32 *returned) +uint32 spoolss_enum_printerdrivers(const char *srv_name, const char *environment, + uint32 level, NEW_BUFFER *buffer, uint32 offered, + uint32 *needed, uint32 *returned) { prs_struct rbuf; prs_struct buf; SPOOL_Q_ENUMPRINTERDRIVERS q_o; SPOOL_R_ENUMPRINTERDRIVERS r_o; + TALLOC_CTX *ctx = prs_get_mem_context(&buffer->prs); struct cli_connection *con = NULL; if (!cli_connection_init(srv_name, PIPE_SPOOLSS, &con)) return False; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, ctx, MARSHALL); + prs_init(&rbuf, 0, 4, ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUM_PRINTERS */ @@ -108,14 +107,15 @@ uint32 spoolss_enum_printers(uint32 flags, fstring srv_name, uint32 level, prs_struct buf; SPOOL_Q_ENUMPRINTERS q_o; SPOOL_R_ENUMPRINTERS r_o; + TALLOC_CTX *ctx = prs_get_mem_context(&buffer->prs); struct cli_connection *con = NULL; if (!cli_connection_init(srv_name, PIPE_SPOOLSS, &con)) return False; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, ctx, MARSHALL); + prs_init(&rbuf, 0, 4, ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUM_PRINTERS */ @@ -172,14 +172,15 @@ uint32 spoolss_enum_ports(fstring srv_name, uint32 level, prs_struct buf; SPOOL_Q_ENUMPORTS q_o; SPOOL_R_ENUMPORTS r_o; + TALLOC_CTX *ctx = prs_get_mem_context(&buffer->prs); struct cli_connection *con = NULL; if (!cli_connection_init(srv_name, PIPE_SPOOLSS, &con)) return False; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, ctx, MARSHALL); + prs_init(&rbuf, 0, 4, ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUMPORTS */ @@ -236,12 +237,13 @@ uint32 spoolss_enum_jobs(const POLICY_HND *hnd, uint32 firstjob, uint32 numofjob prs_struct buf; SPOOL_Q_ENUMJOBS q_o; SPOOL_R_ENUMJOBS r_o; + TALLOC_CTX *ctx = prs_get_mem_context(&buffer->prs); if (hnd == NULL) return NT_STATUS_INVALID_PARAMETER; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, ctx, MARSHALL); + prs_init(&rbuf, 0, 4, ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUMJOBS */ @@ -283,20 +285,26 @@ uint32 spoolss_enum_jobs(const POLICY_HND *hnd, uint32 firstjob, uint32 numofjob do a SPOOLSS Enum printer datas ****************************************************************************/ uint32 spoolss_enum_printerdata(const POLICY_HND *hnd, uint32 idx, - uint32 *valuelen, uint16 *value, uint32 *rvaluelen, - uint32 *type, - uint32 *datalen, uint8 *data, uint32 *rdatalen) + uint32 *valuelen, uint16 *value, uint32 *rvaluelen, + uint32 *type, uint32 *datalen, uint8 *data, + uint32 *rdatalen) { prs_struct rbuf; prs_struct buf; SPOOL_Q_ENUMPRINTERDATA q_o; SPOOL_R_ENUMPRINTERDATA r_o; - + TALLOC_CTX *mem_ctx = NULL; + if (hnd == NULL) return NT_STATUS_INVALID_PARAMETER; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enum_jobs: talloc_init failed!\n")); + return False; + } + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, mem_ctx, MARSHALL); + prs_init(&rbuf, 0, 4, mem_ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUMPRINTERDATA*/ @@ -333,6 +341,8 @@ uint32 spoolss_enum_printerdata(const POLICY_HND *hnd, uint32 idx, prs_mem_free(&rbuf); prs_mem_free(&buf ); + if (mem_ctx) + talloc_destroy(mem_ctx); return r_o.status; } @@ -348,12 +358,13 @@ uint32 spoolss_getprinter(const POLICY_HND *hnd, uint32 level, prs_struct buf; SPOOL_Q_GETPRINTER q_o; SPOOL_R_GETPRINTER r_o; + TALLOC_CTX *ctx = prs_get_mem_context(&buffer->prs); if (hnd == NULL) return NT_STATUS_INVALID_PARAMETER; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, ctx, MARSHALL); + prs_init(&rbuf, 0, 4, ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUMJOBS */ @@ -403,12 +414,13 @@ uint32 spoolss_getprinterdriver(const POLICY_HND *hnd, prs_struct buf; SPOOL_Q_GETPRINTERDRIVER2 q_o; SPOOL_R_GETPRINTERDRIVER2 r_o; + TALLOC_CTX *ctx = prs_get_mem_context(&buffer->prs); if (hnd == NULL) return NT_STATUS_INVALID_PARAMETER; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, ctx, MARSHALL); + prs_init(&rbuf, 0, 4, ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUMJOBS */ @@ -462,9 +474,9 @@ BOOL spoolss_open_printer_ex( const char *printername, BOOL valid_pol = False; fstring srv_name; char *s = NULL; - struct cli_connection *con = NULL; - + TALLOC_CTX *mem_ctx = NULL; + memset(srv_name, 0, sizeof(srv_name)); fstrcpy(srv_name, printername); @@ -475,10 +487,16 @@ BOOL spoolss_open_printer_ex( const char *printername, if (!cli_connection_init(srv_name, PIPE_SPOOLSS, &con)) return False; - if (hnd == NULL) return False; + if (hnd == NULL) + return False; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enum_jobs: talloc_init failed!\n")); + return False; + } + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, mem_ctx, MARSHALL); + prs_init(&rbuf, 0, 4, mem_ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_OPENPRINTEREX */ @@ -517,11 +535,44 @@ BOOL spoolss_open_printer_ex( const char *printername, prs_mem_free(&rbuf); prs_mem_free(&buf ); + if (mem_ctx) + talloc_destroy(mem_ctx); return valid_pol; } /**************************************************************************** + do a SPOOLSS AddPrinterEx() + **ALWAYS** uses as PRINTER_INFO level 2 struct +****************************************************************************/ +BOOL spoolss_addprinterex(POLICY_HND *hnd, PRINTER_INFO_2 *info2) +{ +#if 0 + prs_struct rbuf; + prs_struct buf; + SPOOL_Q_ADDPRINTEREX q_o; + BOOL valid_pol = False; + fstring srv_name; + char *s = NULL; + struct cli_connection *con = NULL; + + + memset(srv_name, 0, sizeof(srv_name)); + unistr_to_ascii(srv_name, info2->servername.buffer, sizeof(srv_name)); + + if (!cli_connection_init(srv_name, PIPE_SPOOLSS, &con)) + return False; + + if (hnd == NULL) return False; + + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); + prs_init(&rbuf, 0, 4, UNMARSHALL); +#endif + + return True; +} + +/**************************************************************************** do a SPOOL Close ****************************************************************************/ BOOL spoolss_closeprinter(POLICY_HND *hnd) @@ -530,14 +581,19 @@ BOOL spoolss_closeprinter(POLICY_HND *hnd) prs_struct buf; SPOOL_Q_CLOSEPRINTER q_c; BOOL valid_close = False; - + TALLOC_CTX *mem_ctx = NULL; + if (hnd == NULL) return False; /* create and send a MSRPC command with api SPOOLSS_CLOSEPRINTER */ - - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enum_jobs: talloc_init failed!\n")); + return False; + } + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, mem_ctx, MARSHALL); + prs_init(&rbuf, 0, 4, mem_ctx, UNMARSHALL); DEBUG(4,("SPOOL Close Printer\n")); @@ -563,6 +619,8 @@ BOOL spoolss_closeprinter(POLICY_HND *hnd) prs_mem_free(&rbuf); prs_mem_free(&buf ); + if (mem_ctx) + talloc_destroy(mem_ctx); /* disassociate with the cli_connection */ RpcHndList_del_connection(hnd); @@ -584,12 +642,18 @@ uint32 spoolss_getprinterdata(const POLICY_HND *hnd, const UNISTR2 *valuename, prs_struct buf; SPOOL_Q_GETPRINTERDATA q_o; SPOOL_R_GETPRINTERDATA r_o; + TALLOC_CTX *mem_ctx = NULL; if (hnd == NULL) return NT_STATUS_INVALID_PARAMETER; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enum_jobs: talloc_init failed!\n")); + return False; + } + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, mem_ctx, MARSHALL); + prs_init(&rbuf, 0, 4, mem_ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_GETPRINTERDATA */ @@ -638,14 +702,15 @@ uint32 spoolss_getprinterdriverdir(fstring srv_name, fstring env_name, uint32 le prs_struct buf; SPOOL_Q_GETPRINTERDRIVERDIR q_o; SPOOL_R_GETPRINTERDRIVERDIR r_o; + TALLOC_CTX *ctx = prs_get_mem_context(&buffer->prs); struct cli_connection *con = NULL; if (!cli_connection_init(srv_name, PIPE_SPOOLSS, &con)) return False; - prs_init(&buf , MAX_PDU_FRAG_LEN, 4, MARSHALL); - prs_init(&rbuf, 0, 4, UNMARSHALL); + prs_init(&buf , MAX_PDU_FRAG_LEN, 4, ctx, MARSHALL); + prs_init(&rbuf, 0, 4, ctx, UNMARSHALL); /* create and send a MSRPC command with api SPOOLSS_ENUM_PRINTERS */ diff --git a/source3/rpc_client/msrpc_spoolss.c b/source3/rpc_client/msrpc_spoolss.c index 3540ebbafc..671be00bc0 100644 --- a/source3/rpc_client/msrpc_spoolss.c +++ b/source3/rpc_client/msrpc_spoolss.c @@ -38,12 +38,12 @@ extern struct user_creds *usr_creds; /******************************************************************** initialize a spoolss NEW_BUFFER. ********************************************************************/ -static void init_buffer(NEW_BUFFER *buffer, uint32 size) +void init_buffer(NEW_BUFFER *buffer, uint32 size, TALLOC_CTX *ctx) { buffer->ptr = (size!=0)? 1:0; buffer->size=size; buffer->string_at_end=size; - prs_init(&buffer->prs, size, 4, MARSHALL); + prs_init(&buffer->prs, size, 4, ctx, MARSHALL); buffer->struct_start = prs_offset(&buffer->prs); } @@ -181,49 +181,47 @@ static void decode_printerdriverdir_info_1(NEW_BUFFER *buffer, DRIVER_DIRECTORY_ /* *info=inf;*/ } - /********************************************************************** - Decode a PORT_INFO_2 struct from a NEW_BUFFER + Decode a PORT_INFO_1 struct from a NEW_BUFFER **********************************************************************/ -void decode_port_info_2(NEW_BUFFER *buffer, uint32 returned, - PORT_INFO_2 **info) +void decode_port_info_1(NEW_BUFFER *buffer, uint32 returned, + PORT_INFO_1 **info) { uint32 i; - PORT_INFO_2 *inf; + PORT_INFO_1 *inf; - inf=(PORT_INFO_2*)malloc(returned*sizeof(PORT_INFO_2)); + inf=(PORT_INFO_1*)malloc(returned*sizeof(PORT_INFO_1)); prs_set_offset(&buffer->prs, 0); for (i=0; i<returned; i++) { - new_smb_io_port_info_2("", buffer, &(inf[i]), 0); + new_smb_io_port_info_1("", buffer, &(inf[i]), 0); } *info=inf; } /********************************************************************** - Decode a PORT_INFO_1 struct from a NEW_BUFFER + Decode a PORT_INFO_2 struct from a NEW_BUFFER **********************************************************************/ -void decode_port_info_1(NEW_BUFFER *buffer, uint32 returned, - PORT_INFO_1 **info) +void decode_port_info_2(NEW_BUFFER *buffer, uint32 returned, + PORT_INFO_2 **info) { uint32 i; - PORT_INFO_1 *inf; + PORT_INFO_2 *inf; - inf=(PORT_INFO_1*)malloc(returned*sizeof(PORT_INFO_1)); + inf=(PORT_INFO_2*)malloc(returned*sizeof(PORT_INFO_2)); prs_set_offset(&buffer->prs, 0); for (i=0; i<returned; i++) { - /* WRITEME!!!! yet to be written --jerry */ - /* new_smb_io_port_info_1("", buffer, &(inf[i]), 0); */ - ;; + new_smb_io_port_info_2("", buffer, &(inf[i]), 0); } *info=inf; } + /**************************************************************************** nt spoolss query ****************************************************************************/ @@ -234,15 +232,21 @@ BOOL msrpc_spoolss_enum_printers(char* srv_name, uint32 flags, NEW_BUFFER buffer; uint32 needed; uint32 returned; + TALLOC_CTX *mem_ctx = NULL; - init_buffer(&buffer, 0); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enum_printers: talloc_init failed!\n")); + return False; + } + init_buffer(&buffer, 0, mem_ctx); /* send a NULL buffer first */ status=spoolss_enum_printers(flags, srv_name, level, &buffer, 0, &needed, &returned); if (status==ERROR_INSUFFICIENT_BUFFER) { - init_buffer(&buffer, needed); + init_buffer(&buffer, needed, mem_ctx); status=spoolss_enum_printers(flags, srv_name, level, &buffer, needed, &needed, &returned); } @@ -250,7 +254,11 @@ BOOL msrpc_spoolss_enum_printers(char* srv_name, uint32 flags, report(out_hnd, "\tstatus:[%d (%x)]\n", status, status); if (status!=NT_STATUS_NO_PROBLEMO) + { + if (mem_ctx) + talloc_destroy(mem_ctx); return False; + } /* is there anything to process? */ if (returned != 0) @@ -272,6 +280,9 @@ BOOL msrpc_spoolss_enum_printers(char* srv_name, uint32 flags, display_printer_info_ctr(out_hnd, ACTION_FOOTER , level, returned, ctr); } + if (mem_ctx) + talloc_destroy(mem_ctx); + return True; } @@ -285,15 +296,22 @@ BOOL msrpc_spoolss_enum_ports(char* srv_name, NEW_BUFFER buffer; uint32 needed; uint32 returned; + TALLOC_CTX *mem_ctx = NULL; + + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enum_ports: talloc_init failed!\n")); + return False; + } - init_buffer(&buffer, 0); + init_buffer(&buffer, 0, mem_ctx); /* send a NULL buffer first */ status=spoolss_enum_ports(srv_name, level, &buffer, 0, &needed, &returned); if (status==ERROR_INSUFFICIENT_BUFFER) { - init_buffer(&buffer, needed); + init_buffer(&buffer, needed, mem_ctx); status=spoolss_enum_ports(srv_name, level, &buffer, needed, &needed, &returned); } @@ -301,7 +319,11 @@ BOOL msrpc_spoolss_enum_ports(char* srv_name, report(out_hnd, "\tstatus:[%d (%x)]\n", status, status); if (status!=NT_STATUS_NO_PROBLEMO) + { + if (mem_ctx) + talloc_destroy(mem_ctx); return False; + } /* is there anything to process? */ if (returned != 0) @@ -322,6 +344,10 @@ BOOL msrpc_spoolss_enum_ports(char* srv_name, display_port_info_ctr(out_hnd, ACTION_ENUMERATE, level, returned, ctr); display_port_info_ctr(out_hnd, ACTION_FOOTER , level, returned, ctr); } + if (mem_ctx) + talloc_destroy(mem_ctx); + + return True; } @@ -343,7 +369,8 @@ uint32 msrpc_spoolss_getprinterdata( const char* printer_name, uint32 size; char *data; UNISTR2 uni_val_name; - + TALLOC_CTX *mem_ctx = NULL; + DEBUG(4,("spoolgetdata - printer: %s server: %s user: %s value: %s\n", printer_name, station, user_name, value_name)); @@ -355,22 +382,33 @@ uint32 msrpc_spoolss_getprinterdata( const char* printer_name, init_unistr2(&uni_val_name, value_name, 0); size = 0; - init_buffer(buffer, size); data = NULL; + + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_getprinterdata: talloc_init failed!\n")); + return False; + } + init_buffer(buffer, size, mem_ctx); + status = spoolss_getprinterdata(&hnd, &uni_val_name, size, type, &size, data, &needed); if (status == ERROR_INSUFFICIENT_BUFFER) { size = needed; - init_buffer(buffer, size); + init_buffer(buffer, size, mem_ctx); data = prs_data_p(&buffer->prs); status = spoolss_getprinterdata(&hnd, &uni_val_name, size, type, &size, data, &needed); } + + if (mem_ctx) + talloc_destroy(mem_ctx); - if (status != NT_STATUS_NO_PROBLEMO) { + if (status != NT_STATUS_NO_PROBLEMO) + { if (!spoolss_closeprinter(&hnd)) return NT_STATUS_ACCESS_DENIED; return status; @@ -399,22 +437,33 @@ BOOL msrpc_spoolss_enum_jobs( const char* printer_name, uint32 returned; uint32 firstjob=0; uint32 numofjobs=0xffff; - + TALLOC_CTX *mem_ctx = NULL; + DEBUG(4,("spoolopen - printer: %s server: %s user: %s\n", printer_name, station, user_name)); if(!spoolss_open_printer_ex( printer_name, 0, 0, station, user_name, &hnd)) return False; - init_buffer(&buffer, 0); - status = spoolss_enum_jobs(&hnd, firstjob, numofjobs, level, &buffer, 0, &needed, &returned); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enum_jobs: talloc_init failed!\n")); + return False; + } + init_buffer(&buffer, 0, mem_ctx); + status = spoolss_enum_jobs(&hnd, firstjob, numofjobs, level, + &buffer, 0, &needed, &returned); if (status == ERROR_INSUFFICIENT_BUFFER) { - init_buffer(&buffer, needed); - status = spoolss_enum_jobs( &hnd, firstjob, numofjobs, level, &buffer, needed, &needed, &returned); + init_buffer(&buffer, needed, mem_ctx); + status = spoolss_enum_jobs( &hnd, firstjob, numofjobs, level, + &buffer, needed, &needed, &returned); } + if (mem_ctx) + talloc_destroy(mem_ctx); + if (status!=NT_STATUS_NO_PROBLEMO) { if (!spoolss_closeprinter(&hnd)) return False; @@ -446,8 +495,8 @@ BOOL msrpc_spoolss_enum_printerdata( const char* printer_name, uint32 rdatalen; uint32 maxvaluelen; uint32 maxdatalen; - - DEBUG(4,("spoolenum_printerdata - printer: %s\n", printer_name)); + + DEBUG(4,("msrpc_spoolss_enum_printerdata - printer: %s\n", printer_name)); if(!spoolss_open_printer_ex( printer_name, 0, 0, station, user_name, &hnd)) return False; @@ -519,25 +568,35 @@ BOOL msrpc_spoolss_getprinter( const char* printer_name, const uint32 level, uint32 status=0; NEW_BUFFER buffer; uint32 needed=1000; - + TALLOC_CTX *mem_ctx = NULL; + DEBUG(4,("spoolenum_getprinter - printer: %s\n", printer_name)); if(!spoolss_open_printer_ex( printer_name, "", PRINTER_ALL_ACCESS, station, user_name, &hnd)) return False; - init_buffer(&buffer, needed); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_getprinter: talloc_init failed!\n")); + return False; + } + init_buffer(&buffer, needed, mem_ctx); status = spoolss_getprinter(&hnd, level, &buffer, needed, &needed); if (status==ERROR_INSUFFICIENT_BUFFER) { - init_buffer(&buffer, needed); + init_buffer(&buffer, needed, mem_ctx); status = spoolss_getprinter(&hnd, level, &buffer, needed, &needed); } report(out_hnd, "\tstatus:[%d (%x)]\n", status, status); if (status!=NT_STATUS_NO_PROBLEMO) + { + if (mem_ctx) + talloc_destroy(mem_ctx); return False; + } switch (level) { case 0: @@ -558,6 +617,9 @@ BOOL msrpc_spoolss_getprinter( const char* printer_name, const uint32 level, display_printer_info_ctr(out_hnd, ACTION_ENUMERATE, level, 1, ctr); display_printer_info_ctr(out_hnd, ACTION_FOOTER , level, 1, ctr); + if (mem_ctx) + talloc_destroy(mem_ctx); + if (status!=NT_STATUS_NO_PROBLEMO) { if (!spoolss_closeprinter(&hnd)) return False; @@ -579,25 +641,35 @@ BOOL msrpc_spoolss_getprinterdriver( const char* printer_name, uint32 status=0; NEW_BUFFER buffer; uint32 needed; - - DEBUG(4,("spoolenum_getprinterdriver - printer: %s\n", printer_name)); + TALLOC_CTX *mem_ctx = NULL; + + DEBUG(4,("msrpc_spoolss_enum_getprinterdriver - printer: %s\n", printer_name)); if(!spoolss_open_printer_ex( printer_name, "", PRINTER_ALL_ACCESS, station, user_name, &hnd)) return False; - init_buffer(&buffer, 0); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_getprinterdriver: talloc_init failed!\n")); + return False; + } + init_buffer(&buffer, 0, mem_ctx); status = spoolss_getprinterdriver(&hnd, environment, level, &buffer, 0, &needed); if (status==ERROR_INSUFFICIENT_BUFFER) { - init_buffer(&buffer, needed); + init_buffer(&buffer, needed, mem_ctx); status = spoolss_getprinterdriver(&hnd, environment, level, &buffer, needed, &needed); } report(out_hnd, "\tstatus:[%d (%x)]\n", status, status); if (status!=NT_STATUS_NO_PROBLEMO) + { + if (mem_ctx) + talloc_destroy(mem_ctx); return False; + } switch (level) { case 1: @@ -615,6 +687,9 @@ BOOL msrpc_spoolss_getprinterdriver( const char* printer_name, display_printer_driver_ctr(out_hnd, ACTION_ENUMERATE, level, 1, ctr); display_printer_driver_ctr(out_hnd, ACTION_FOOTER , level, 1, ctr); + if (mem_ctx) + talloc_destroy(mem_ctx); + if (status!=NT_STATUS_NO_PROBLEMO) { if (!spoolss_closeprinter(&hnd)) return False; @@ -635,17 +710,23 @@ BOOL msrpc_spoolss_enumprinterdrivers( const char* srv_name, NEW_BUFFER buffer; uint32 needed; uint32 returned; + TALLOC_CTX *mem_ctx = NULL; + + DEBUG(4,("msrpc_spoolss_enum_enumprinterdrivers - server: %s\n", srv_name)); - DEBUG(4,("spoolenum_enumprinterdrivers - server: %s\n", srv_name)); - - init_buffer(&buffer, 0); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_enumprinterdrivers: talloc_init failed!\n")); + return False; + } + init_buffer(&buffer, 0, mem_ctx); status = spoolss_enum_printerdrivers(srv_name, environment, level, &buffer, 0, &needed, &returned); if (status == ERROR_INSUFFICIENT_BUFFER) { - init_buffer(&buffer, needed); + init_buffer(&buffer, needed, mem_ctx); status = spoolss_enum_printerdrivers( srv_name, environment, level, &buffer, needed, &needed, &returned); } @@ -653,7 +734,11 @@ BOOL msrpc_spoolss_enumprinterdrivers( const char* srv_name, report(out_hnd, "\tstatus:[%d (%x)]\n", status, status); if (status!=NT_STATUS_NO_PROBLEMO) + { + if (mem_ctx) + talloc_destroy(mem_ctx); return False; + } switch (level) { @@ -678,6 +763,9 @@ BOOL msrpc_spoolss_enumprinterdrivers( const char* srv_name, display_printer_driver_ctr(out_hnd, ACTION_ENUMERATE, level, returned, ctr); display_printer_driver_ctr(out_hnd, ACTION_FOOTER , level, returned, ctr); + if (mem_ctx) + talloc_destroy(mem_ctx); + return True; } @@ -688,26 +776,32 @@ BOOL msrpc_spoolss_getprinterdriverdir(char* srv_name, char* env_name, uint32 le { uint32 status; NEW_BUFFER buffer; - uint32 needed = 502; - - init_buffer(&buffer, 0); + uint32 needed; + TALLOC_CTX *mem_ctx = NULL; + + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0,("msrpc_spoolss_getprinterdriverdir: talloc_init failed!\n")); + return False; + } + init_buffer(&buffer, 0, mem_ctx); -#if 0 /* JERRY */ /* send a NULL buffer first */ status=spoolss_getprinterdriverdir(srv_name, env_name, level, &buffer, 0, &needed); if (status==ERROR_INSUFFICIENT_BUFFER) { -#endif - init_buffer(&buffer, needed); + init_buffer(&buffer, needed, mem_ctx); status=spoolss_getprinterdriverdir(srv_name, env_name, level, &buffer, needed, &needed); -#if 0 } -#endif report(out_hnd, "\tstatus:[%d (%x)]\n", status, status); if (status!=NT_STATUS_NO_PROBLEMO) + { + if (mem_ctx) + talloc_destroy(mem_ctx); return False; + } switch (level) { case 1: @@ -718,6 +812,10 @@ BOOL msrpc_spoolss_getprinterdriverdir(char* srv_name, char* env_name, uint32 le display_printerdriverdir_info_ctr(out_hnd, ACTION_HEADER , level, ctr); display_printerdriverdir_info_ctr(out_hnd, ACTION_ENUMERATE, level, ctr); display_printerdriverdir_info_ctr(out_hnd, ACTION_FOOTER , level, ctr); + + if (mem_ctx) + talloc_destroy(mem_ctx); + return True; } diff --git a/source3/rpcclient/cmd_spoolss.c b/source3/rpcclient/cmd_spoolss.c index 00d5a4d7d1..5a614a38b5 100644 --- a/source3/rpcclient/cmd_spoolss.c +++ b/source3/rpcclient/cmd_spoolss.c @@ -102,14 +102,22 @@ nt spoolss query uint32 cmd_spoolss_enum_ports(struct client_info *info, int argc, char *argv[]) { PORT_INFO_CTR ctr; + uint32 level; + fstring srv_name; - uint32 level = 2; + if (argc < 1) + { + report (out_hnd, "spoolenumports <level>\n"); + return NT_STATUS_INVALID_PARAMETER; + } - fstring srv_name; + fstrcpy(srv_name, "\\\\"); fstrcat(srv_name, info->dest_host); strupper(srv_name); + level = atoi(argv[1]); + if (msrpc_spoolss_enum_ports(srv_name, level, &ctr)) DEBUG(5,("cmd_spoolss_enum_printer: query succeeded\n")); else @@ -489,9 +497,6 @@ uint32 cmd_spoolss_getprinterdriverdir(struct client_info *info, int argc, char ********************************************************************************/ uint32 cmd_spoolss_addprinterex(struct client_info *info, int argc, char *argv[]) { -#if 0 - PRINTER_INFO_CTR ctr; - uint32 level = 2; fstring srv_name, printer_name, driver_name, @@ -506,25 +511,32 @@ uint32 cmd_spoolss_addprinterex(struct client_info *info, int argc, char *argv[] uint32 i; fstring srv_port_name; BOOL valid_port = False; + TALLOC_CTX *mem_ctx = NULL; fstrcpy(srv_name, "\\\\"); fstrcat(srv_name, info->dest_host); strupper(srv_name); /* check (and copy) the command line arguments */ - if (argc < 2) { - report(out_hnd, "spooladdprinterex <name> <driver>\n"); + if (argc < 3) { + report(out_hnd, "spooladdprinterex <name> <driver> <port>\n"); return NT_STATUS_NOPROBLEMO; } - - fstrcpy(printer_name, argv[1]); - fstrcpy(driver_name, argv[2]); - fstrcpy(port_name, argv[3]); - + else + { + fstrcpy(printer_name, argv[1]); + fstrcpy(driver_name, argv[2]); + fstrcpy(port_name, argv[3]); + } /* Verify that the specified port is ok; spoolss_enum_ports() should be a level 1 since all we need is the name */ - init_buffer (&buffer, 0); + if ((mem_ctx=talloc_init()) == NULL) + { + DEBUG(0, ("cmd_spoolss_addprinterex: talloc_init() failed!\n")); + return NT_STATUS_INVALID_PARAMETER; + } + init_buffer (&buffer, 0, mem_ctx); /* send a NULL buffer first */ status=spoolss_enum_ports(srv_name, 1, &buffer, 0, @@ -532,7 +544,7 @@ uint32 cmd_spoolss_addprinterex(struct client_info *info, int argc, char *argv[] /* send the right amount of space this time */ if (status==ERROR_INSUFFICIENT_BUFFER) { - init_buffer(&buffer, needed); + init_buffer(&buffer, needed, mem_ctx); status=spoolss_enum_ports(srv_name, 1, &buffer, needed, &needed, &returned); @@ -540,11 +552,11 @@ uint32 cmd_spoolss_addprinterex(struct client_info *info, int argc, char *argv[] an PRINTER_INFO_1 structre */ if (status == NT_STATUS_NO_PROBLEMO) { - decode_port_info_1 (&buffer, returned, &port_info_1); + decode_port_info_1(&buffer, returned, &port_info_1); } else { - report (out_hnd, "cmd_spoolss_addprinterex: FAILED to enumerate ports\n")); + report (out_hnd, "cmd_spoolss_addprinterex: FAILED to enumerate ports\n"); return NT_STATUS_NOPROBLEMO; } @@ -558,7 +570,8 @@ uint32 cmd_spoolss_addprinterex(struct client_info *info, int argc, char *argv[] for (i=0; i<returned; i++) { /* compare port_info_1[i].port_name to the port_name specified */ - unistr_to_ascii(srv_port_name, port_info_1[i].port_name, sizeof(srv_port_name)-1); + unistr_to_ascii(srv_port_name, port_info_1[i].port_name.buffer, + sizeof(srv_port_name)-1); if (strequal(srv_port_name, port_name)) { valid_port = True; @@ -573,13 +586,39 @@ uint32 cmd_spoolss_addprinterex(struct client_info *info, int argc, char *argv[] /* - * Need to build the PRINTER_INFO_2 struct here + * Need to build the PRINTER_INFO_2 struct here. + * I think it would be better only to deal with a PRINTER_INFO_2 + * and the abstract the creation of a SPOOL_PRINTER_INFO_LEVEL_2 + * from that rather than dealing with the struct passed dircetly + * on the wire. We don't need the extra *_ptr fields, etc... + * here anyways. --jerry */ - ;; - + init_unistr( &print_info_2.servername, srv_name); + init_unistr( &print_info_2.printername, printer_name); + init_unistr( &print_info_2.sharename, printer_name); + init_unistr( &print_info_2.portname, port_name); + init_unistr( &print_info_2.drivername, driver_name); + init_unistr( &print_info_2.comment, "Created by rpcclient"); + init_unistr( &print_info_2.location, ""); + init_unistr (&print_info_2.sepfile, ""); + init_unistr( &print_info_2.printprocessor, "winprint"); + init_unistr( &print_info_2.datatype, "RAW"); + init_unistr( &print_info_2.parameters, ""); + print_info_2.devmode = NULL; + print_info_2.secdesc = NULL; + print_info_2.attributes = 0; + print_info_2.priority = 0; + print_info_2.defaultpriority = 0; + print_info_2.starttime = 0; + print_info_2.untiltime = 0; + print_info_2.status = 0; + print_info_2.cjobs = 0; + print_info_2.averageppm = 0; + + /* if successful, spoolss_addprinterex() should return True and hnd should be a valid handle to an open printer */ - if (spoolss_addprinterex(&hnd, 2, &print_info_2)) + if (spoolss_addprinterex(&hnd, &print_info_2)) { if (!spoolss_closeprinter( &hnd )) { @@ -592,8 +631,14 @@ uint32 cmd_spoolss_addprinterex(struct client_info *info, int argc, char *argv[] } -#endif return NT_STATUS_NOPROBLEMO; } - +/******************************************************************************** + send an AddPrinterDriver() request +********************************************************************************/ +uint32 cmd_spoolss_addprinterdriver(struct client_info *info, int argc, char *argv[]) +{ + + return NT_STATUS_NOPROBLEMO; +} diff --git a/source3/rpcclient/display_spool.c b/source3/rpcclient/display_spool.c index f2e9deccbd..1a88eed5ad 100644 --- a/source3/rpcclient/display_spool.c +++ b/source3/rpcclient/display_spool.c @@ -298,6 +298,28 @@ void display_printer_info_ctr(FILE *out_hnd, enum action_type action, uint32 lev /**************************************************************************** connection info level 3 container display function ****************************************************************************/ +static void display_port_info_1_ctr(FILE *out_hnd, enum action_type action, + uint32 count, PORT_INFO_CTR *ctr) +{ + uint32 i = 0; + switch (action) + { + case ACTION_HEADER: + report(out_hnd, "Port Info Level 1:\n"); + break; + case ACTION_ENUMERATE: + for (i=0; i<count; i++) + display_port_info_1(out_hnd, action, &ctr->port.info_1[i]); + break; + case ACTION_FOOTER: + report(out_hnd, "\n"); + break; + } +} + +/**************************************************************************** +connection info level 3 container display function +****************************************************************************/ static void display_port_info_2_ctr(FILE *out_hnd, enum action_type action, uint32 count, PORT_INFO_CTR *ctr) { @@ -324,6 +346,9 @@ void display_port_info_ctr(FILE *out_hnd, enum action_type action, uint32 level, uint32 count, PORT_INFO_CTR *ctr) { switch (level) { + case 1: + display_port_info_1_ctr(out_hnd, action, count, ctr); + break; case 2: display_port_info_2_ctr(out_hnd, action, count, ctr); break; @@ -333,6 +358,27 @@ void display_port_info_ctr(FILE *out_hnd, enum action_type action, uint32 level, } } +/**************************************************************************** +connection info container display function +****************************************************************************/ +void display_port_info_1(FILE *out_hnd, enum action_type action, PORT_INFO_1 *i1) +{ + fstring buffer; + + switch (action) + { + case ACTION_HEADER: + report(out_hnd, "Port:\n"); + break; + case ACTION_ENUMERATE: + unistr_to_ascii(buffer, i1->port_name.buffer, sizeof(buffer)-1); + fprintf (out_hnd, "\tPort Name:\t[%s]\n\n", buffer); + break; + case ACTION_FOOTER: + report(out_hnd, "\n"); + break; + } +} /**************************************************************************** connection info container display function diff --git a/source3/rpcclient/spoolss_cmds.c b/source3/rpcclient/spoolss_cmds.c index 1041ae158c..b010aa4874 100644 --- a/source3/rpcclient/spoolss_cmds.c +++ b/source3/rpcclient/spoolss_cmds.c @@ -38,7 +38,7 @@ static const struct command_set spl_commands[] = { {NULL, NULL}}, {"spoolenumports", cmd_spoolss_enum_ports, - "Enumerate Ports", + "<port info level> Enumerate Ports", {NULL, NULL}}, {"spoolenumdatas", cmd_spoolss_enum_printerdata, @@ -72,7 +72,12 @@ static const struct command_set spl_commands[] = { {"spooladdprinter", cmd_spoolss_addprinterex, "<name> <driver> Spool AddPrinterEx()", {NULL, NULL}}, - /* + + {"spooladdprinterdriver", cmd_spoolss_addprinterdriver, + "<driver> Spool AddPrinterDriver()", + {NULL, NULL}}, + + /* * oop! */ {"", NULL, NULL, {NULL, NULL}} |