From ac42cd59f27de7d753fafd12b4c667073b8758c1 Mon Sep 17 00:00:00 2001 From: Gerald Carter Date: Fri, 5 Aug 2005 00:58:31 +0000 Subject: r9086: * fix invalid read in parse_spoolss when writing a devmode to the wire * fix dup_a_regval() when size is 0 * ensure we pass a pstring to unlink_internals (fixes delete_driver code) (This used to be commit 353e63ff421c564a1b7c7cfe95982f31c871a227) --- source3/printing/nt_printing.c | 37 ++++++++++++++++++++++--------------- source3/registry/reg_objects.c | 7 ++++++- source3/rpc_parse/parse_spoolss.c | 30 ++++++++++++++++++++++++------ 3 files changed, 52 insertions(+), 22 deletions(-) diff --git a/source3/printing/nt_printing.c b/source3/printing/nt_printing.c index a7ba46cd51..f6e9e2306f 100644 --- a/source3/printing/nt_printing.c +++ b/source3/printing/nt_printing.c @@ -2102,19 +2102,20 @@ static WERROR get_a_printer_driver_3(NT_PRINTER_DRIVER_INFO_LEVEL_3 **info_ptr, fstring *tddfs; tddfs = SMB_REALLOC_ARRAY(driver.dependentfiles, fstring, i+2); - if (tddfs == NULL) { + if ( !tddfs ) { DEBUG(0,("get_a_printer_driver_3: failed to enlarge buffer!\n")); break; } - else driver.dependentfiles = tddfs; + else + driver.dependentfiles = tddfs; len += tdb_unpack(dbuf.dptr+len, dbuf.dsize-len, "f", &driver.dependentfiles[i]); i++; } - if (driver.dependentfiles != NULL) - fstrcpy(driver.dependentfiles[i], ""); + if ( driver.dependentfiles ) + fstrcpy( driver.dependentfiles[i], "" ); SAFE_FREE(dbuf.dptr); @@ -4944,6 +4945,7 @@ static BOOL delete_driver_files( NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3, struct { int i = 0; char *s; + pstring file; connection_struct *conn; DATA_BLOB null_pw; NTSTATUS nt_status; @@ -4985,45 +4987,50 @@ static BOOL delete_driver_files( NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3, struct if ( *info_3->driverpath ) { if ( (s = strchr( &info_3->driverpath[1], '\\' )) != NULL ) { - driver_unix_convert(s, conn, NULL, &bad_path, &st); + pstrcpy( file, s ); + driver_unix_convert(file, conn, NULL, &bad_path, &st); DEBUG(10,("deleting driverfile [%s]\n", s)); - unlink_internals(conn, 0, s); + unlink_internals(conn, 0, file); } } if ( *info_3->configfile ) { if ( (s = strchr( &info_3->configfile[1], '\\' )) != NULL ) { - driver_unix_convert(s, conn, NULL, &bad_path, &st); + pstrcpy( file, s ); + driver_unix_convert(file, conn, NULL, &bad_path, &st); DEBUG(10,("deleting configfile [%s]\n", s)); - unlink_internals(conn, 0, s); + unlink_internals(conn, 0, file); } } if ( *info_3->datafile ) { if ( (s = strchr( &info_3->datafile[1], '\\' )) != NULL ) { - driver_unix_convert(s, conn, NULL, &bad_path, &st); + pstrcpy( file, s ); + driver_unix_convert(file, conn, NULL, &bad_path, &st); DEBUG(10,("deleting datafile [%s]\n", s)); - unlink_internals(conn, 0, s); + unlink_internals(conn, 0, file); } } if ( *info_3->helpfile ) { if ( (s = strchr( &info_3->helpfile[1], '\\' )) != NULL ) { - driver_unix_convert(s, conn, NULL, &bad_path, &st); + pstrcpy( file, s ); + driver_unix_convert(file, conn, NULL, &bad_path, &st); DEBUG(10,("deleting helpfile [%s]\n", s)); - unlink_internals(conn, 0, s); + unlink_internals(conn, 0, file); } } /* check if we are done removing files */ if ( info_3->dependentfiles ) { - while ( *info_3->dependentfiles[i] ) { - char *file; + while ( info_3->dependentfiles[i][0] ) { + char *p; /* bypass the "\print$" portion of the path */ - if ( (file = strchr( info_3->dependentfiles[i]+1, '\\' )) != NULL ) { + if ( (p = strchr( info_3->dependentfiles[i]+1, '\\' )) != NULL ) { + pstrcpy( file, p ); driver_unix_convert(file, conn, NULL, &bad_path, &st); DEBUG(10,("deleting dependent file [%s]\n", file)); unlink_internals(conn, 0, file ); diff --git a/source3/registry/reg_objects.c b/source3/registry/reg_objects.c index d6482e698b..b5753fc688 100644 --- a/source3/registry/reg_objects.c +++ b/source3/registry/reg_objects.c @@ -194,13 +194,18 @@ REGISTRY_VALUE* dup_registry_value( REGISTRY_VALUE *val ) /* copy all the non-pointer initial data */ memcpy( copy, val, sizeof(REGISTRY_VALUE) ); - if ( val->data_p ) + + copy->size = 0; + copy->data_p = NULL; + + if ( val->data_p && val->size ) { if ( !(copy->data_p = memdup( val->data_p, val->size )) ) { DEBUG(0,("dup_registry_value: memdup() failed for [%d] bytes!\n", val->size)); SAFE_FREE( copy ); } + copy->size = val->size; } return copy; diff --git a/source3/rpc_parse/parse_spoolss.c b/source3/rpc_parse/parse_spoolss.c index 2663b09381..2677a4a2df 100644 --- a/source3/rpc_parse/parse_spoolss.c +++ b/source3/rpc_parse/parse_spoolss.c @@ -631,6 +631,8 @@ BOOL spoolss_io_devmode(const char *desc, prs_struct *ps, int depth, DEVICEMODE int available_space; /* size of the device mode left to parse */ /* only important on unmarshalling */ int i = 0; + uint16 *unistr_buffer; + int j; struct optional_fields { fstring name; @@ -662,12 +664,20 @@ BOOL spoolss_io_devmode(const char *desc, prs_struct *ps, int depth, DEVICEMODE depth++; if (UNMARSHALLING(ps)) { - devmode->devicename.buffer = PRS_ALLOC_MEM(ps, uint16, 32); + devmode->devicename.buffer = PRS_ALLOC_MEM(ps, uint16, MAXDEVICENAME); if (devmode->devicename.buffer == NULL) return False; + unistr_buffer = devmode->devicename.buffer; } - - if (!prs_uint16uni(True,"devicename", ps, depth, devmode->devicename.buffer, MAXDEVICENAME)) + else { + /* devicename is a static sized string but the buffer we set is not */ + unistr_buffer = PRS_ALLOC_MEM(ps, uint16, MAXDEVICENAME); + memset( unistr_buffer, 0x0, MAXDEVICENAME ); + for ( j=0; devmode->devicename.buffer[j]; j++ ) + unistr_buffer[j] = devmode->devicename.buffer[j]; + } + + if (!prs_uint16uni(True,"devicename", ps, depth, unistr_buffer, MAXDEVICENAME)) return False; if (!prs_uint16("specversion", ps, depth, &devmode->specversion)) @@ -709,12 +719,20 @@ BOOL spoolss_io_devmode(const char *desc, prs_struct *ps, int depth, DEVICEMODE return False; if (UNMARSHALLING(ps)) { - devmode->formname.buffer = PRS_ALLOC_MEM(ps, uint16, 32); + devmode->formname.buffer = PRS_ALLOC_MEM(ps, uint16, MAXDEVICENAME); if (devmode->formname.buffer == NULL) return False; + unistr_buffer = devmode->formname.buffer; } - - if (!prs_uint16uni(True, "formname", ps, depth, devmode->formname.buffer, 32)) + else { + /* devicename is a static sized string but the buffer we set is not */ + unistr_buffer = PRS_ALLOC_MEM(ps, uint16, MAXDEVICENAME); + memset( unistr_buffer, 0x0, MAXDEVICENAME ); + for ( j=0; devmode->formname.buffer[j]; j++ ) + unistr_buffer[j] = devmode->formname.buffer[j]; + } + + if (!prs_uint16uni(True, "formname", ps, depth, unistr_buffer, MAXDEVICENAME)) return False; if (!prs_uint16("logpixels", ps, depth, &devmode->logpixels)) return False; -- cgit