Index: cgi-bin/var.c =================================================================== RCS file: /development/cvs/cups/cgi-bin/var.c,v retrieving revision 1.21 retrieving revision 1.22 diff -u -r1.21 -r1.22 --- cgi-bin/var.c 2002/01/02 17:58:37 1.21 +++ cgi-bin/var.c 2002/12/12 20:56:29 1.22 @@ -242,7 +242,7 @@ var_t *var; /* Returned variable */ - if (name == NULL || value == NULL || element < 0) + if (name == NULL || value == NULL || element < 0 || element > 100000) return; if ((var = cgi_find_variable(name)) == NULL) @@ -286,7 +286,7 @@ var_t *var; /* Returned variable */ - if (name == NULL || size < 0) + if (name == NULL || size < 0 || size > 100000) return; if ((var = cgi_find_variable(name)) == NULL) @@ -361,7 +361,7 @@ var_t *var; /* New variable */ - if (name == NULL || value == NULL) + if (name == NULL || value == NULL || element < 0 || element > 100000) return; #ifdef DEBUG Index: conf/cupsd.conf.in =================================================================== RCS file: /development/cvs/cups/conf/cupsd.conf.in,v retrieving revision 1.7 retrieving revision 1.8 diff -u -r1.7 -r1.8 --- conf/cupsd.conf.in.orig 2001-09-14 18:52:05.000000000 +0200 +++ conf/cupsd.conf.in 2002-12-17 13:36:34.000000000 +0100 @@ -358,6 +358,15 @@ #MaxClients 100 # +# MaxClientsPerHost: controls the maximum number of simultaneous clients that +# will be handled from a specific host. Defaults to 10 or 1/10th of the +# MaxClients setting, whichever is larger. A value of 0 specifies the +# automatic (10 or 1/10th) setting. +# + +#MaxClientsPerHost 0 + +# # MaxRequestSize: controls the maximum size of HTTP requests and print files. # Set to 0 to disable this feature (defaults to 0.) # Index: cups/http.c =================================================================== RCS file: /development/cvs/cups/cups/http.c,v retrieving revision 1.105 retrieving revision 1.107 diff -u -r1.105 -r1.107 --- cups/http.c 2002/10/30 20:04:56 1.105 +++ cups/http.c 2002/12/12 21:44:42 1.107 @@ -896,11 +896,16 @@ } http->data_remaining = strtol(len, NULL, 16); + if (http->data_remaining < 0) + { + DEBUG_puts("httpRead: Negative chunk length!"); + return (0); + } } DEBUG_printf(("httpRead: data_remaining = %d\n", http->data_remaining)); - if (http->data_remaining == 0) + if (http->data_remaining <= 0) { /* * A zero-length chunk ends a transfer; unless we are reading POST Index: filter/image-bmp.c =================================================================== RCS file: /development/cvs/cups/filter/image-bmp.c,v retrieving revision 1.8 retrieving revision 1.9 diff -u -r1.8 -r1.9 --- filter/image-bmp.c 2002/04/19 16:17:26 1.8 +++ filter/image-bmp.c 2002/12/13 15:52:20 1.9 @@ -105,8 +105,15 @@ read_word(fp); offset = read_dword(fp); - fprintf(stderr, "offset = %d\n", offset); + fprintf(stderr, "DEBUG: offset = %d\n", offset); + if (offset < 0) + { + fprintf(stderr, "ERROR: Bad BMP offset %d\n", offset); + fclose(fp); + return (1); + } + /* * Then the bitmap information... */ @@ -123,15 +130,34 @@ colors_used = read_dword(fp); colors_important = read_dword(fp); + if (img->xsize == 0 || img->xsize > IMAGE_MAX_WIDTH || + img->ysize == 0 || img->ysize > IMAGE_MAX_HEIGHT || + (depth != 1 && depth != 4 && depth != 8 && depth != 24)) + { + fprintf(stderr, "ERROR: Bad BMP dimensions %ux%ux%d\n", + img->xsize, img->ysize, depth); + fclose(fp); + return (1); + } + + if (colors_used < 0 || colors_used > 256) + { + fprintf(stderr, "ERROR: Bad BMP colormap size %d\n", colors_used); + fclose(fp); + return (1); + } + + if (img->xppi == 0 || img->yppi == 0) + { + fprintf(stderr, "ERROR: Bad BMP resolution %dx%d PPI.\n", + img->xppi, img->yppi); + img->xppi = img->yppi = 128; + } + /* * Make sure the resolution info is valid... */ - if (img->xppi == 0) - img->xppi = 128; - if (img->yppi == 0) - img->yppi = 128; - fprintf(stderr, "info_size = %d, xsize = %d, ysize = %d, planes = %d, depth = %d\n", info_size, img->xsize, img->ysize, planes, depth); fprintf(stderr, "compression = %d, image_size = %d, xppi = %d, yppi = %d\n", @@ -150,7 +176,8 @@ if (colors_used == 0 && depth <= 8) colors_used = 1 << depth; - fread(colormap, colors_used, 4, fp); + if (colors_used > 0) + fread(colormap, colors_used, 4, fp); /* * Setup image and buffers... Index: filter/image-gif.c =================================================================== RCS file: /development/cvs/cups/filter/image-gif.c,v retrieving revision 1.13 retrieving revision 1.15 diff -u -r1.13 -r1.15 --- filter/image-gif.c 2002/11/27 04:43:53 1.13 +++ filter/image-gif.c 2002/12/13 15:52:20 1.15 @@ -233,6 +233,19 @@ img->xsize = (buf[5] << 8) | buf[4]; img->ysize = (buf[7] << 8) | buf[6]; + /* + * Check the dimensions of the image; since the dimensions are + * a 16-bit integer we just need to check for 0... + */ + + if (img->xsize == 0 || img->ysize == 0) + { + fprintf(stderr, "ERROR: Bad GIF image dimensions: %dx%d\n", + img->xsize, img->ysize); + fclose(fp); + return (1); + } + i = gif_read_image(fp, img, cmap, buf[8] & GIF_INTERLACE); fclose(fp); return (i); Index: filter/image-jpeg.c =================================================================== RCS file: /development/cvs/cups/filter/image-jpeg.c,v retrieving revision 1.15 retrieving revision 1.16 diff -u -r1.15 -r1.16 --- filter/image-jpeg.c 2002/04/19 16:17:26 1.15 +++ filter/image-jpeg.c 2002/12/13 15:52:20 1.16 @@ -126,6 +126,18 @@ jpeg_calc_output_dimensions(&cinfo); + if (cinfo.output_width <= 0 || cinfo.output_width > IMAGE_MAX_WIDTH || + cinfo.output_height <= 0 || cinfo.output_height > IMAGE_MAX_HEIGHT) + { + fprintf(stderr, "ERROR: Bad JPEG dimensions %dx%d!\n", + cinfo.output_width, cinfo.output_height); + + jpeg_destroy_decompress(&cinfo); + + fclose(fp); + return (1); + } + img->xsize = cinfo.output_width; img->ysize = cinfo.output_height; @@ -141,6 +153,13 @@ img->xppi = (int)((float)cinfo.X_density * 2.54); img->yppi = (int)((float)cinfo.Y_density * 2.54); } + + if (img->xppi == 0 || img->yppi == 0) + { + fprintf(stderr, "ERROR: Bad JPEG image resolution %dx%d PPI.\n", + img->xppi, img->yppi); + img->xppi = img->yppi = 128; + } } fprintf(stderr, "DEBUG: JPEG image %dx%dx%d, %dx%d PPI\n", Index: filter/image-pix.c =================================================================== RCS file: /development/cvs/cups/filter/image-pix.c,v retrieving revision 1.6 retrieving revision 1.7 diff -u -r1.6 -r1.7 --- filter/image-pix.c 2002/04/19 16:17:27 1.6 +++ filter/image-pix.c 2002/12/13 15:52:20 1.7 @@ -78,6 +78,21 @@ read_short(fp); depth = read_short(fp); + /* + * Check the dimensions of the image. Since the short values used for the + * width and height cannot exceed IMAGE_MAX_WIDTH or IMAGE_MAX_HEIGHT, we + * just need to verify they are positive integers. + */ + + if (width <= 0 || height <= 0 || + (depth != 8 && depth != 24)) + { + fprintf(stderr, "ERROR: Bad PIX image dimensions %dx%dx%d\n", + width, height, depth); + fclose(fp); + return (1); + } + if (depth == 8) img->colorspace = secondary; else Index: filter/image-png.c =================================================================== RCS file: /development/cvs/cups/filter/image-png.c,v retrieving revision 1.14 retrieving revision 1.15 diff -u -r1.14 -r1.15 --- filter/image-png.c 2002/04/19 16:17:27 1.14 +++ filter/image-png.c 2002/12/13 15:52:20 1.15 @@ -90,6 +90,15 @@ else img->colorspace = (primary == IMAGE_RGB_CMYK) ? IMAGE_RGB : primary; + if (info->width == 0 || info->width > IMAGE_MAX_WIDTH || + info->height == 0 || info->height > IMAGE_MAX_HEIGHT) + { + fprintf(stderr, "ERROR: PNG image has invalid dimensions %ux%u!\n", + (unsigned)info->width, (unsigned)info->height); + fclose(fp); + return (1); + } + img->xsize = info->width; img->ysize = info->height; @@ -98,6 +107,14 @@ { img->xppi = (int)((float)info->x_pixels_per_unit * 0.0254); img->yppi = (int)((float)info->y_pixels_per_unit * 0.0254); + + if (img->xppi == 0 || img->yppi == 0) + { + fprintf(stderr, "ERROR: PNG image has invalid resolution %dx%d PPI\n", + img->xppi, img->yppi); + + img->xppi = img->yppi = 128; + } } ImageSetMaxTiles(img, 0); Index: filter/image-pnm.c =================================================================== RCS file: /development/cvs/cups/filter/image-pnm.c,v retrieving revision 1.10 retrieving revision 1.11 diff -u -r1.10 -r1.11 --- filter/image-pnm.c 2002/04/19 16:17:27 1.10 +++ filter/image-pnm.c 2002/12/13 15:52:20 1.11 @@ -132,6 +132,22 @@ else maxval = 1; + if (img->xsize == 0 || img->xsize > IMAGE_MAX_WIDTH || + img->ysize == 0 || img->ysize > IMAGE_MAX_HEIGHT) + { + fprintf(stderr, "ERROR: Bad PNM dimensions %dx%d!\n", + img->xsize, img->ysize); + fclose(fp); + return (1); + } + + if (maxval == 0) + { + fprintf(stderr, "ERROR: Bad PNM max value %d!\n", maxval); + fclose(fp); + return (1); + } + if (format == 1 || format == 2 || format == 4 || format == 5) img->colorspace = secondary; else Index: filter/image-sgi.c =================================================================== RCS file: /development/cvs/cups/filter/image-sgi.c,v retrieving revision 1.11 retrieving revision 1.12 diff -u -r1.11 -r1.12 --- filter/image-sgi.c 2002/04/19 16:17:27 1.11 +++ filter/image-sgi.c 2002/12/13 15:52:20 1.12 @@ -73,6 +73,22 @@ * Get the image dimensions and load the output image... */ + /* + * Check the image dimensions; since xsize and ysize are unsigned shorts, + * just check if they are 0 since they can't exceed IMAGE_MAX_WIDTH or + * IMAGE_MAX_HEIGHT... + */ + + if (sgip->xsize == 0 || sgip->ysize == 0 || + sgip->zsize == 0 || sgip->zsize > 4) + { + fprintf(stderr, "ERROR: Bad SGI image dimensions %ux%ux%u!\n", + sgip->xsize, sgip->ysize, sgip->zsize); + sgiClose(sgip); + fclose(fp); + return (1); + } + if (sgip->zsize < 3) img->colorspace = secondary; else Index: filter/image-sun.c =================================================================== RCS file: /development/cvs/cups/filter/image-sun.c,v retrieving revision 1.12 retrieving revision 1.14 diff -u -r1.12 -r1.14 --- filter/image-sun.c 2002/10/22 18:43:45 1.12 +++ filter/image-sun.c 2002/12/13 15:52:20 1.14 @@ -121,6 +121,15 @@ fprintf(stderr, "DEBUG: ras_width=%d, ras_height=%d, ras_depth=%d, ras_type=%d, ras_maplength=%d\n", img->xsize, img->ysize, ras_depth, ras_type, ras_maplength); + if (ras_maplength > 768 || + img->xsize == 0 || img->xsize > IMAGE_MAX_WIDTH || + img->ysize == 0 || img->ysize > IMAGE_MAX_HEIGHT || + ras_depth == 0 || ras_depth > 32) + { + fputs("ERROR: Raster image cannot be loaded!\n", stderr); + return (1); + } + if (ras_maplength > 0) { memset(cmap[0], 255, sizeof(cmap[0])); Index: filter/image-tiff.c =================================================================== RCS file: /development/cvs/cups/filter/image-tiff.c,v retrieving revision 1.23 retrieving revision 1.24 diff -u -r1.23 -r1.24 --- filter/image-tiff.c 2002/04/19 16:17:27 1.23 +++ filter/image-tiff.c 2002/12/13 15:52:21 1.24 @@ -173,6 +173,12 @@ img->yppi = 128; } + if (img->xppi == 0 || img->yppi == 0) + { + fputs("ERROR: Bad TIFF resolution.\n", stderr); + img->xppi = img->yppi = 128; + } + fprintf(stderr, "DEBUG: TIFF resolution = %fx%f, units=%d\n", xres, yres, resunit); fprintf(stderr, "DEBUG: Stored resolution = %dx%d PPI\n", @@ -189,6 +195,23 @@ alpha = 0; /* + * Check the size of the image... + */ + + if (width == 0 || width > IMAGE_MAX_WIDTH || + height == 0 || height > IMAGE_MAX_HEIGHT || + (bits != 1 && bits != 2 && bits != 4 && bits != 8) || + samples < 1 || samples > 4) + { + fprintf(stderr, "ERROR: Bad TIFF dimensions %ux%ux%ux%u!\n", + (unsigned)width, (unsigned)height, (unsigned)bits, + (unsigned)samples); + TIFFClose(tif); + fclose(fp); + return (1); + } + + /* * Setup the image size and colorspace... */ Index: filter/image-zoom.c =================================================================== RCS file: /development/cvs/cups/filter/image-zoom.c,v retrieving revision 1.10 retrieving revision 1.11 diff -u -r1.10 -r1.11 --- filter/image-zoom.c 2002/08/27 16:19:38 1.10 +++ filter/image-zoom.c 2002/12/13 15:52:21 1.11 @@ -58,6 +58,12 @@ int flip; /* Flip on X axis? */ + if (xsize > IMAGE_MAX_WIDTH || + ysize > IMAGE_MAX_HEIGHT || + (x1 - x0) > IMAGE_MAX_WIDTH || + (y1 - y0) > IMAGE_MAX_HEIGHT) + return (NULL); /* Protect against integer overflow */ + if ((z = (izoom_t *)calloc(1, sizeof(izoom_t))) == NULL) return (NULL); Index: filter/image.h =================================================================== RCS file: /development/cvs/cups/filter/image.h,v retrieving revision 1.15 retrieving revision 1.16 diff -u -r1.15 -r1.16 --- filter/image.h 2002/04/29 15:56:58 1.15 +++ filter/image.h 2002/12/13 15:52:21 1.16 @@ -40,6 +40,13 @@ /* + * Maximum image dimensions that we can handle... + */ + +# define IMAGE_MAX_WIDTH 0x07ffffff /* 2^27-1 to allow for 15-channel data */ +# define IMAGE_MAX_HEIGHT 0x7fffffff /* 2^31-1 */ + +/* * Colorspaces... */ @@ -50,7 +57,6 @@ # define IMAGE_RGB 3 /* Red, green, and blue */ # define IMAGE_RGB_CMYK 4 /* Use RGB or CMYK */ - /* * Tile definitions... */ Index: scheduler/client.c =================================================================== RCS file: /development/cvs/cups/scheduler/client.c,v retrieving revision 1.128 retrieving revision 1.130 diff -u -r1.128 -r1.130 --- scheduler/client.c 2002/11/21 14:58:18 1.128 +++ scheduler/client.c 2002/12/13 16:24:05 1.130 @@ -492,6 +520,12 @@ LogMessage(L_DEBUG2, "ReadClient() %d, used=%d", con->http.fd, con->http.used); + if (con->http.error) + { + CloseClient(con); + return (0); + } + switch (con->http.state) { case HTTP_WAITING : @@ -944,6 +978,20 @@ break; } + else if (atoi(con->http.fields[HTTP_FIELD_CONTENT_LENGTH]) < 0) + { + /* + * Negative content lengths are invalid! + */ + + if (!SendError(con, HTTP_BAD_REQUEST)) + { + CloseClient(con); + return (0); + } + + break; + } /* * See what kind of POST request this is; for IPP requests the Index: scheduler/dirsvc.c =================================================================== RCS file: /development/cvs/cups/scheduler/dirsvc.c,v retrieving revision 1.100 retrieving revision 1.101 diff -u -r1.100 -r1.101 --- scheduler/dirsvc.c 2002/09/26 15:19:31 1.100 +++ scheduler/dirsvc.c 2002/12/12 20:56:32 1.101 @@ -88,6 +88,31 @@ httpSeparate(uri, method, username, host, &port, resource); /* + * Determine if the URI contains any illegal characters in it... + */ + + if (strncmp(uri, "ipp://", 6) != 0 || + !host[0] || + (strncmp(resource, "/printers/", 10) != 0 && + strncmp(resource, "/classes/", 9) != 0)) + { + LogMessage(L_ERROR, "ProcessBrowseData: Bad printer URI in browse data: %s", + uri); + return; + } + + if (strchr(resource, '?') != NULL || + (strncmp(resource, "/printers/", 10) == 0 && + strchr(resource + 10, '/') != NULL) || + (strncmp(resource, "/classes/", 9) == 0 && + strchr(resource + 9, '/') != NULL)) + { + LogMessage(L_ERROR, "ProcessBrowseData: Bad resource in browse data: %s", + resource); + return; + } + + /* * OK, this isn't a local printer; see if we already have it listed in * the Printers list, and add it if not... */