diff options
author | Andreas Schneider <asn@samba.org> | 2016-11-15 14:29:29 +0100 |
---|---|---|
committer | Jeremy Allison <jra@samba.org> | 2016-11-20 17:29:07 +0100 |
commit | 4d9f4bfc69a5899bdf91406dfb7efb70a530446c (patch) | |
tree | 0a1e92ca74c90a1eac050beea2fef2361c4ececc | |
parent | 4f702e4b4463319db6d7638901834611a665b884 (diff) | |
download | samba-4d9f4bfc69a5899bdf91406dfb7efb70a530446c.tar.gz |
s3:spoolss: Add support for COPY_FROM_DIRECTORY in AddPrinterDriverEx
BUG: https://bugzilla.samba.org/show_bug.cgi?id=12415
Signed-off-by: Andreas Schneider <asn@samba.org>
Reviewed-by: Jeremy Allison <jra@samba.org>
-rw-r--r-- | source3/include/nt_printing.h | 7 | ||||
-rw-r--r-- | source3/printing/nt_printing.c | 96 | ||||
-rw-r--r-- | source3/rpc_server/spoolss/srv_spoolss_nt.c | 18 |
3 files changed, 100 insertions, 21 deletions
diff --git a/source3/include/nt_printing.h b/source3/include/nt_printing.h index e253658fa20..e0003f98762 100644 --- a/source3/include/nt_printing.h +++ b/source3/include/nt_printing.h @@ -170,11 +170,14 @@ bool delete_driver_files(const struct auth_session_info *server_info, const struct spoolss_DriverInfo8 *r); WERROR move_driver_to_download_area(struct auth_session_info *session_info, - struct spoolss_AddDriverInfoCtr *r); + struct spoolss_AddDriverInfoCtr *r, + const char *driver_directory); WERROR clean_up_driver_struct(TALLOC_CTX *mem_ctx, struct auth_session_info *session_info, - struct spoolss_AddDriverInfoCtr *r); + struct spoolss_AddDriverInfoCtr *r, + uint32_t flags, + const char **driver_directory); void map_printer_permissions(struct security_descriptor *sd); diff --git a/source3/printing/nt_printing.c b/source3/printing/nt_printing.c index 334a56e7556..394a3e5e7e1 100644 --- a/source3/printing/nt_printing.c +++ b/source3/printing/nt_printing.c @@ -864,7 +864,9 @@ static WERROR clean_up_driver_struct_level(TALLOC_CTX *mem_ctx, const char **config_file, const char **help_file, struct spoolss_StringArray *dependent_files, - enum spoolss_DriverOSVersion *version) + enum spoolss_DriverOSVersion *version, + uint32_t flags, + const char **driver_directory) { const char *short_architecture; int i; @@ -879,6 +881,43 @@ static WERROR clean_up_driver_struct_level(TALLOC_CTX *mem_ctx, return WERR_INVALID_PARAMETER; } + if (flags & APD_COPY_FROM_DIRECTORY) { + char *path; + char *q; + + /* + * driver_path is set to: + * + * \\PRINTSRV\print$\x64\{279245b0-a8bd-4431-bf6f-baee92ac15c0}\pscript5.dll + */ + path = talloc_strdup(mem_ctx, *driver_path); + if (path == NULL) { + return WERR_NOT_ENOUGH_MEMORY; + } + + /* Remove pscript5.dll */ + q = strrchr_m(path, '\\'); + if (q == NULL) { + return WERR_INVALID_PARAMETER; + } + *q = '\0'; + + /* Get \{279245b0-a8bd-4431-bf6f-baee92ac15c0} */ + q = strrchr_m(path, '\\'); + if (q == NULL) { + return WERR_INVALID_PARAMETER; + } + + /* + * Set driver_directory to: + * + * {279245b0-a8bd-4431-bf6f-baee92ac15c0} + * + * This is the directory where all the files have been uploaded + */ + *driver_directory = q + 1; + } + /* clean up the driver name. * we can get .\driver.dll * or worse c:\windows\system\driver.dll ! @@ -931,7 +970,9 @@ static WERROR clean_up_driver_struct_level(TALLOC_CTX *mem_ctx, WERROR clean_up_driver_struct(TALLOC_CTX *mem_ctx, struct auth_session_info *session_info, - struct spoolss_AddDriverInfoCtr *r) + struct spoolss_AddDriverInfoCtr *r, + uint32_t flags, + const char **driver_directory) { switch (r->level) { case 3: @@ -942,7 +983,9 @@ WERROR clean_up_driver_struct(TALLOC_CTX *mem_ctx, &r->info.info3->config_file, &r->info.info3->help_file, r->info.info3->dependent_files, - &r->info.info3->version); + &r->info.info3->version, + flags, + driver_directory); case 6: return clean_up_driver_struct_level(mem_ctx, session_info, r->info.info6->architecture, @@ -951,7 +994,9 @@ WERROR clean_up_driver_struct(TALLOC_CTX *mem_ctx, &r->info.info6->config_file, &r->info.info6->help_file, r->info.info6->dependent_files, - &r->info.info6->version); + &r->info.info6->version, + flags, + driver_directory); case 8: return clean_up_driver_struct_level(mem_ctx, session_info, r->info.info8->architecture, @@ -960,7 +1005,9 @@ WERROR clean_up_driver_struct(TALLOC_CTX *mem_ctx, &r->info.info8->config_file, &r->info.info8->help_file, r->info.info8->dependent_files, - &r->info.info8->version); + &r->info.info8->version, + flags, + driver_directory); default: return WERR_NOT_SUPPORTED; } @@ -1012,7 +1059,8 @@ static WERROR move_driver_file_to_download_area(TALLOC_CTX *mem_ctx, const char *driver_file, const char *short_architecture, uint32_t driver_version, - uint32_t version) + uint32_t version, + const char *driver_directory) { struct smb_filename *smb_fname_old = NULL; struct smb_filename *smb_fname_new = NULL; @@ -1021,9 +1069,21 @@ static WERROR move_driver_file_to_download_area(TALLOC_CTX *mem_ctx, NTSTATUS status; WERROR ret; - old_name = talloc_asprintf(mem_ctx, "%s/%s", - short_architecture, driver_file); - W_ERROR_HAVE_NO_MEMORY(old_name); + if (driver_directory != NULL) { + old_name = talloc_asprintf(mem_ctx, + "%s/%s/%s", + short_architecture, + driver_directory, + driver_file); + } else { + old_name = talloc_asprintf(mem_ctx, + "%s/%s", + short_architecture, + driver_file); + } + if (old_name == NULL) { + return WERR_NOT_ENOUGH_MEMORY; + } new_name = talloc_asprintf(mem_ctx, "%s/%d/%s", short_architecture, driver_version, driver_file); @@ -1076,7 +1136,8 @@ static WERROR move_driver_file_to_download_area(TALLOC_CTX *mem_ctx, } WERROR move_driver_to_download_area(struct auth_session_info *session_info, - struct spoolss_AddDriverInfoCtr *r) + struct spoolss_AddDriverInfoCtr *r, + const char *driver_directory) { struct spoolss_AddDriverInfo3 *driver; struct spoolss_AddDriverInfo3 converted_driver; @@ -1201,7 +1262,8 @@ WERROR move_driver_to_download_area(struct auth_session_info *session_info, driver->driver_path, short_architecture, driver->version, - ver); + ver, + driver_directory); if (!W_ERROR_IS_OK(err)) { goto err_exit; } @@ -1215,7 +1277,8 @@ WERROR move_driver_to_download_area(struct auth_session_info *session_info, driver->data_file, short_architecture, driver->version, - ver); + ver, + driver_directory); if (!W_ERROR_IS_OK(err)) { goto err_exit; } @@ -1231,7 +1294,8 @@ WERROR move_driver_to_download_area(struct auth_session_info *session_info, driver->config_file, short_architecture, driver->version, - ver); + ver, + driver_directory); if (!W_ERROR_IS_OK(err)) { goto err_exit; } @@ -1248,7 +1312,8 @@ WERROR move_driver_to_download_area(struct auth_session_info *session_info, driver->help_file, short_architecture, driver->version, - ver); + ver, + driver_directory); if (!W_ERROR_IS_OK(err)) { goto err_exit; } @@ -1273,7 +1338,8 @@ WERROR move_driver_to_download_area(struct auth_session_info *session_info, driver->dependent_files->string[i], short_architecture, driver->version, - ver); + ver, + driver_directory); if (!W_ERROR_IS_OK(err)) { goto err_exit; } diff --git a/source3/rpc_server/spoolss/srv_spoolss_nt.c b/source3/rpc_server/spoolss/srv_spoolss_nt.c index 2b28332acec..2e19cf43d5f 100644 --- a/source3/rpc_server/spoolss/srv_spoolss_nt.c +++ b/source3/rpc_server/spoolss/srv_spoolss_nt.c @@ -8567,7 +8567,9 @@ WERROR _spoolss_AddPrinterDriverEx(struct pipes_struct *p, { WERROR err = WERR_OK; const char *driver_name = NULL; + const char *driver_directory = NULL; uint32_t version; + /* * we only support the semantics of AddPrinterDriver() * i.e. only copy files that are newer than existing ones @@ -8577,7 +8579,8 @@ WERROR _spoolss_AddPrinterDriverEx(struct pipes_struct *p, return WERR_INVALID_PARAMETER; } - if (r->in.flags != APD_COPY_NEW_FILES) { + if (!(r->in.flags & APD_COPY_ALL_FILES) && + !(r->in.flags & APD_COPY_NEW_FILES)) { return WERR_ACCESS_DENIED; } @@ -8591,12 +8594,19 @@ WERROR _spoolss_AddPrinterDriverEx(struct pipes_struct *p, } DEBUG(5,("Cleaning driver's information\n")); - err = clean_up_driver_struct(p->mem_ctx, p->session_info, r->in.info_ctr); - if (!W_ERROR_IS_OK(err)) + err = clean_up_driver_struct(p->mem_ctx, + p->session_info, + r->in.info_ctr, + r->in.flags, + &driver_directory); + if (!W_ERROR_IS_OK(err)) { goto done; + } DEBUG(5,("Moving driver to final destination\n")); - err = move_driver_to_download_area(p->session_info, r->in.info_ctr); + err = move_driver_to_download_area(p->session_info, + r->in.info_ctr, + driver_directory); if (!W_ERROR_IS_OK(err)) { goto done; } |