Main Page   Modules   Alphabetical List   Data Structures   File List   Data Fields   Globals  

src/main/print-util.c

Go to the documentation of this file.
00001 /*
00002  * "$Id: print-util.c,v 1.105 2004/05/09 16:06:11 rleigh Exp $"
00003  *
00004  *   Print plug-in driver utility functions for the GIMP.
00005  *
00006  *   Copyright 1997-2000 Michael Sweet (mike@easysw.com) and
00007  *      Robert Krawitz (rlk@alum.mit.edu)
00008  *
00009  *   This program is free software; you can redistribute it and/or modify it
00010  *   under the terms of the GNU General Public License as published by the Free
00011  *   Software Foundation; either version 2 of the License, or (at your option)
00012  *   any later version.
00013  *
00014  *   This program is distributed in the hope that it will be useful, but
00015  *   WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
00016  *   or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
00017  *   for more details.
00018  *
00019  *   You should have received a copy of the GNU General Public License
00020  *   along with this program; if not, write to the Free Software
00021  *   Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00022  */
00023 
00024 /*
00025  * This file must include only standard C header files.  The core code must
00026  * compile on generic platforms that don't support glib, gimp, gtk, etc.
00027  */
00028 
00029 #ifdef HAVE_CONFIG_H
00030 #include <config.h>
00031 #endif
00032 #include <gimp-print/gimp-print.h>
00033 #include "gimp-print-internal.h"
00034 #include <gimp-print/gimp-print-intl-internal.h>
00035 #include <math.h>
00036 #include <limits.h>
00037 #if defined(HAVE_VARARGS_H) && !defined(HAVE_STDARG_H)
00038 #include <varargs.h>
00039 #else
00040 #include <stdarg.h>
00041 #endif
00042 #include <string.h>
00043 #include <stdio.h>
00044 #include <stdlib.h>
00045 #include <sys/types.h>
00046 #include <sys/stat.h>
00047 #include <unistd.h>
00048 #include "generic-options.h"
00049 
00050 #define FMIN(a, b) ((a) < (b) ? (a) : (b))
00051 
00052 typedef struct
00053 {
00054   stp_outfunc_t ofunc;
00055   void *odata;
00056   char *data;
00057   size_t bytes;
00058 } debug_msgbuf_t;
00059 
00060 /*
00061  * We cannot avoid use of the (non-ANSI) vsnprintf here; ANSI does
00062  * not provide a safe, length-limited sprintf function.
00063  */
00064 
00065 #define STPI_VASPRINTF(result, bytes, format)                           \
00066 {                                                                       \
00067   int current_allocation = 64;                                          \
00068   result = stp_malloc(current_allocation);                              \
00069   while (1)                                                             \
00070     {                                                                   \
00071       va_list args;                                                     \
00072       va_start(args, format);                                           \
00073       bytes = vsnprintf(result, current_allocation, format, args);      \
00074       va_end(args);                                                     \
00075       if (bytes >= 0 && bytes < current_allocation)                     \
00076         break;                                                          \
00077       else                                                              \
00078         {                                                               \
00079           stp_free (result);                                            \
00080           if (bytes < 0)                                                \
00081             current_allocation *= 2;                                    \
00082           else                                                          \
00083             current_allocation = bytes + 1;                             \
00084           result = stp_malloc(current_allocation);                      \
00085         }                                                               \
00086     }                                                                   \
00087 }
00088 
00089 void
00090 stp_zprintf(const stp_vars_t *v, const char *format, ...)
00091 {
00092   char *result;
00093   int bytes;
00094   STPI_VASPRINTF(result, bytes, format);
00095   (stp_get_outfunc(v))((void *)(stp_get_outdata(v)), result, bytes);
00096   stp_free(result);
00097 }
00098 
00099 void
00100 stp_asprintf(char **strp, const char *format, ...)
00101 {
00102   char *result;
00103   int bytes;
00104   STPI_VASPRINTF(result, bytes, format);
00105   *strp = result;
00106 }
00107 
00108 void
00109 stp_catprintf(char **strp, const char *format, ...)
00110 {
00111   char *result1;
00112   char *result2;
00113   int bytes;
00114   STPI_VASPRINTF(result1, bytes, format);
00115   stp_asprintf(&result2, "%s%s", *strp, result1);
00116   stp_free(result1);
00117   *strp = result2;
00118 }
00119 
00120 
00121 void
00122 stp_zfwrite(const char *buf, size_t bytes, size_t nitems, const stp_vars_t *v)
00123 {
00124   (stp_get_outfunc(v))((void *)(stp_get_outdata(v)), buf, bytes * nitems);
00125 }
00126 
00127 void
00128 stp_putc(int ch, const stp_vars_t *v)
00129 {
00130   unsigned char a = (unsigned char) ch;
00131   (stp_get_outfunc(v))((void *)(stp_get_outdata(v)), (char *) &a, 1);
00132 }
00133 
00134 #define BYTE(expr, byteno) (((expr) >> (8 * byteno)) & 0xff)
00135 
00136 void
00137 stp_put16_le(unsigned short sh, const stp_vars_t *v)
00138 {
00139   stp_putc(BYTE(sh, 0), v);
00140   stp_putc(BYTE(sh, 1), v);
00141 }
00142 
00143 void
00144 stp_put16_be(unsigned short sh, const stp_vars_t *v)
00145 {
00146   stp_putc(BYTE(sh, 1), v);
00147   stp_putc(BYTE(sh, 0), v);
00148 }
00149 
00150 void
00151 stp_put32_le(unsigned int in, const stp_vars_t *v)
00152 {
00153   stp_putc(BYTE(in, 0), v);
00154   stp_putc(BYTE(in, 1), v);
00155   stp_putc(BYTE(in, 2), v);
00156   stp_putc(BYTE(in, 3), v);
00157 }
00158 
00159 void
00160 stp_put32_be(unsigned int in, const stp_vars_t *v)
00161 {
00162   stp_putc(BYTE(in, 3), v);
00163   stp_putc(BYTE(in, 2), v);
00164   stp_putc(BYTE(in, 1), v);
00165   stp_putc(BYTE(in, 0), v);
00166 }
00167 
00168 void
00169 stp_puts(const char *s, const stp_vars_t *v)
00170 {
00171   (stp_get_outfunc(v))((void *)(stp_get_outdata(v)), s, strlen(s));
00172 }
00173 
00174 void
00175 stp_send_command(const stp_vars_t *v, const char *command,
00176                  const char *format, ...)
00177 {
00178   int i = 0;
00179   char fchar;
00180   const char *out_str;
00181   unsigned short byte_count = 0;
00182   va_list args;
00183 
00184   if (strlen(format) > 0)
00185     {
00186       va_start(args, format);
00187       for (i = 0; i < strlen(format); i++)
00188         {
00189           switch (format[i])
00190             {
00191             case 'a':
00192             case 'b':
00193             case 'B':
00194             case 'd':
00195             case 'D':
00196               break;
00197             case 'c':
00198               (void) va_arg(args, unsigned int);
00199               byte_count += 1;
00200               break;
00201             case 'h':
00202             case 'H':
00203               (void) va_arg(args, unsigned int);
00204               byte_count += 2;
00205               break;
00206             case 'l':
00207             case 'L':
00208               (void) va_arg(args, unsigned int);
00209               byte_count += 4;
00210               break;
00211             case 's':
00212               out_str = va_arg(args, const char *);
00213               byte_count += strlen(out_str);
00214               break;
00215             }
00216         }
00217       va_end(args);
00218     }
00219 
00220   stp_puts(command, v);
00221 
00222   va_start(args, format);
00223   while ((fchar = format[0]) != '\0')
00224     {
00225       switch (fchar)
00226         {
00227         case 'a':
00228           stp_putc(byte_count, v);
00229           break;
00230         case 'b':
00231           stp_put16_le(byte_count, v);
00232           break;
00233         case 'B':
00234           stp_put16_be(byte_count, v);
00235           break;
00236         case 'd':
00237           stp_put32_le(byte_count, v);
00238           break;
00239         case 'D':
00240           stp_put32_be(byte_count, v);
00241           break;
00242         case 'c':
00243           stp_putc(va_arg(args, unsigned int), v);
00244           break;
00245         case 'h':
00246           stp_put16_le(va_arg(args, unsigned int), v);
00247           break;
00248         case 'H':
00249           stp_put16_be(va_arg(args, unsigned int), v);
00250           break;
00251         case 'l':
00252           stp_put32_le(va_arg(args, unsigned int), v);
00253           break;
00254         case 'L':
00255           stp_put32_be(va_arg(args, unsigned int), v);
00256           break;
00257         case 's':
00258           stp_puts(va_arg(args, const char *), v);
00259           break;
00260         }
00261       format++;
00262     }
00263   va_end(args);
00264 }
00265 
00266 void
00267 stp_eprintf(const stp_vars_t *v, const char *format, ...)
00268 {
00269   int bytes;
00270   if (stp_get_errfunc(v))
00271     {
00272       char *result;
00273       STPI_VASPRINTF(result, bytes, format);
00274       (stp_get_errfunc(v))((void *)(stp_get_errdata(v)), result, bytes);
00275       stp_free(result);
00276     }
00277   else
00278     {
00279       va_list args;
00280       va_start(args, format);
00281       vfprintf(stderr, format, args);
00282       va_end(args);
00283     }
00284 }
00285 
00286 void
00287 stp_erputc(int ch)
00288 {
00289   putc(ch, stderr);
00290 }
00291 
00292 void
00293 stp_erprintf(const char *format, ...)
00294 {
00295   va_list args;
00296   va_start(args, format);
00297   vfprintf(stderr, format, args);
00298   va_end(args);
00299 }
00300 
00301 static unsigned long stpi_debug_level = 0;
00302 
00303 static void
00304 stpi_init_debug(void)
00305 {
00306   static int debug_initialized = 0;
00307   if (!debug_initialized)
00308     {
00309       const char *dval = getenv("STP_DEBUG");
00310       debug_initialized = 1;
00311       if (dval)
00312         {
00313           stpi_debug_level = strtoul(dval, 0, 0);
00314           stp_erprintf("Gimp-Print %s %s\n", VERSION, RELEASE_DATE);
00315         }
00316     }
00317 }
00318 
00319 unsigned long
00320 stp_get_debug_level(void)
00321 {
00322   stpi_init_debug();
00323   return stpi_debug_level;
00324 }
00325 
00326 void
00327 stp_dprintf(unsigned long level, const stp_vars_t *v, const char *format, ...)
00328 {
00329   int bytes;
00330   stpi_init_debug();
00331   if ((level & stpi_debug_level) && stp_get_errfunc(v))
00332     {
00333       char *result;
00334       STPI_VASPRINTF(result, bytes, format);
00335       (stp_get_errfunc(v))((void *)(stp_get_errdata(v)), result, bytes);
00336       stp_free(result);
00337     }
00338 }
00339 
00340 void
00341 stp_deprintf(unsigned long level, const char *format, ...)
00342 {
00343   va_list args;
00344   va_start(args, format);
00345   stpi_init_debug();
00346   if (level & stpi_debug_level)
00347     vfprintf(stderr, format, args);
00348   va_end(args);
00349 }
00350 
00351 static void
00352 fill_buffer_writefunc(void *priv, const char *buffer, size_t bytes)
00353 {
00354   debug_msgbuf_t *msgbuf = (debug_msgbuf_t *) priv;
00355   if (msgbuf->bytes == 0)
00356     msgbuf->data = stp_malloc(bytes + 1);
00357   else
00358     msgbuf->data = stp_realloc(msgbuf->data, msgbuf->bytes + bytes + 1);
00359   memcpy(msgbuf->data + msgbuf->bytes, buffer, bytes);
00360   msgbuf->bytes += bytes;
00361   msgbuf->data[msgbuf->bytes] = '\0';
00362 }
00363 
00364 void
00365 stp_init_debug_messages(stp_vars_t *v)
00366 {
00367   int verified_flag = stp_get_verified(v);
00368   debug_msgbuf_t *msgbuf = stp_malloc(sizeof(debug_msgbuf_t));
00369   msgbuf->ofunc = stp_get_errfunc(v);
00370   msgbuf->odata = stp_get_errdata(v);
00371   msgbuf->data = NULL;
00372   msgbuf->bytes = 0;
00373   stp_set_errfunc((stp_vars_t *) v, fill_buffer_writefunc);
00374   stp_set_errdata((stp_vars_t *) v, msgbuf);
00375   stp_set_verified((stp_vars_t *) v, verified_flag);
00376 }
00377 
00378 void
00379 stp_flush_debug_messages(stp_vars_t *v)
00380 {
00381   int verified_flag = stp_get_verified(v);
00382   debug_msgbuf_t *msgbuf = (debug_msgbuf_t *)stp_get_errdata(v);
00383   stp_set_errfunc((stp_vars_t *) v, msgbuf->ofunc);
00384   stp_set_errdata((stp_vars_t *) v, msgbuf->odata);
00385   stp_set_verified((stp_vars_t *) v, verified_flag);
00386   if (msgbuf->bytes > 0)
00387     {
00388       stp_eprintf(v, "%s", msgbuf->data);
00389       stp_free(msgbuf->data);
00390     }
00391   stp_free(msgbuf);
00392 }
00393 
00394 /* pointers to the allocation functions to use, which may be set by
00395    client applications */
00396 void *(*stp_malloc_func)(size_t size) = malloc;
00397 void *(*stpi_realloc_func)(void *ptr, size_t size) = realloc;
00398 void (*stpi_free_func)(void *ptr) = free;
00399 
00400 void *
00401 stp_malloc (size_t size)
00402 {
00403   register void *memptr = NULL;
00404 
00405   if ((memptr = stp_malloc_func (size)) == NULL)
00406     {
00407       fputs("Virtual memory exhausted.\n", stderr);
00408       stp_abort();
00409     }
00410   return (memptr);
00411 }
00412 
00413 void *
00414 stp_zalloc (size_t size)
00415 {
00416   register void *memptr = stp_malloc(size);
00417   (void) memset(memptr, 0, size);
00418   return (memptr);
00419 }
00420 
00421 void *
00422 stp_realloc (void *ptr, size_t size)
00423 {
00424   register void *memptr = NULL;
00425 
00426   if (size > 0 && ((memptr = stpi_realloc_func (ptr, size)) == NULL))
00427     {
00428       fputs("Virtual memory exhausted.\n", stderr);
00429       stp_abort();
00430     }
00431   return (memptr);
00432 }
00433 
00434 void
00435 stp_free(void *ptr)
00436 {
00437   stpi_free_func(ptr);
00438 }
00439 
00440 int
00441 stp_init(void)
00442 {
00443   static int stpi_is_initialised = 0;
00444   if (!stpi_is_initialised)
00445     {
00446       /* Things that are only initialised once */
00447       /* Set up gettext */
00448 #ifdef ENABLE_NLS
00449       setlocale (LC_ALL, "");
00450       bindtextdomain (PACKAGE, PACKAGE_LOCALE_DIR);
00451 #endif
00452       stpi_init_debug();
00453       stp_xml_preinit();
00454       stpi_init_printer();
00455       stpi_init_paper();
00456       stpi_init_dither();
00457       /* Load modules */
00458       if (stp_module_load())
00459         return 1;
00460       /* Load XML data */
00461       if (stp_xml_init_defaults())
00462         return 1;
00463       /* Initialise modules */
00464       if (stp_module_init())
00465         return 1;
00466       /* Set up defaults for core parameters */
00467       stp_initialize_printer_defaults();
00468     }
00469 
00470   stpi_is_initialised = 1;
00471   return 0;
00472 }
00473 
00474 size_t
00475 stp_strlen(const char *s)
00476 {
00477   return strlen(s);
00478 }
00479 
00480 char *
00481 stp_strndup(const char *s, int n)
00482 {
00483   char *ret;
00484   if (!s || n < 0)
00485     {
00486       ret = stp_malloc(1);
00487       ret[0] = 0;
00488       return ret;
00489     }
00490   else
00491     {
00492       ret = stp_malloc(n + 1);
00493       memcpy(ret, s, n);
00494       ret[n] = 0;
00495       return ret;
00496     }
00497 }
00498 
00499 char *
00500 stp_strdup(const char *s)
00501 {
00502   char *ret;
00503   if (!s)
00504     {
00505       ret = stp_malloc(1);
00506       ret[0] = '\0';
00507       return ret;
00508     }
00509   else
00510     return stp_strndup(s, stp_strlen(s));
00511 }
00512 
00513 const char *
00514 stp_set_output_codeset(const char *codeset)
00515 {
00516 #ifdef ENABLE_NLS
00517   return (const char *)(bind_textdomain_codeset(PACKAGE, codeset));
00518 #else
00519   return "US-ASCII";
00520 #endif
00521 }
00522 
00523 stp_curve_t *
00524 stp_read_and_compose_curves(const char *s1, const char *s2,
00525                             stp_curve_compose_t comp)
00526 {
00527   stp_curve_t *ret = NULL;
00528   stp_curve_t *t1 = NULL;
00529   stp_curve_t *t2 = NULL;
00530   if (s1)
00531     t1 = stp_curve_create_from_string(s1);
00532   if (s2)
00533     t2 = stp_curve_create_from_string(s2);
00534   if (t1 && t2)
00535     stp_curve_compose(&ret, t1, t2, comp, -1);
00536   if (ret)
00537     {
00538       stp_curve_destroy(t1);
00539       stp_curve_destroy(t2);
00540       return ret;
00541     }
00542   else if (t1)
00543     {
00544       stp_curve_destroy(t2);
00545       return t1;
00546     }
00547   else
00548     return t2;
00549 }
00550 
00551 void
00552 stp_merge_printvars(stp_vars_t *user, const stp_vars_t *print)
00553 {
00554   int i;
00555   stp_parameter_list_t params = stp_get_parameter_list(print);
00556   int count = stp_parameter_list_count(params);
00557   for (i = 0; i < count; i++)
00558     {
00559       const stp_parameter_t *p = stp_parameter_list_param(params, i);
00560       if (p->p_type == STP_PARAMETER_TYPE_DOUBLE &&
00561           p->p_class == STP_PARAMETER_CLASS_OUTPUT &&
00562           stp_check_float_parameter(print, p->name, STP_PARAMETER_DEFAULTED))
00563         {
00564           stp_parameter_t desc;
00565           double prnval = stp_get_float_parameter(print, p->name);
00566           double usrval;
00567           stp_describe_parameter(print, p->name, &desc);
00568           if (stp_check_float_parameter(user, p->name, STP_PARAMETER_ACTIVE))
00569             usrval = stp_get_float_parameter(user, p->name);
00570           else
00571             usrval = desc.deflt.dbl;
00572           if (strcmp(p->name, "Gamma") == 0)
00573             usrval /= prnval;
00574           else
00575             usrval *= prnval;
00576           if (usrval < desc.bounds.dbl.lower)
00577             usrval = desc.bounds.dbl.lower;
00578           else if (usrval > desc.bounds.dbl.upper)
00579             usrval = desc.bounds.dbl.upper;
00580           stp_set_float_parameter(user, p->name, usrval);
00581           stp_parameter_description_destroy(&desc);
00582         }
00583     }
00584   stp_parameter_list_destroy(params);
00585 }
00586 
00587 stp_parameter_list_t
00588 stp_get_parameter_list(const stp_vars_t *v)
00589 {
00590   stp_parameter_list_t ret = stp_parameter_list_create();
00591   stp_parameter_list_t tmp_list;
00592 
00593   tmp_list = stp_printer_list_parameters(v);
00594   stp_parameter_list_append(ret, tmp_list);
00595   stp_parameter_list_destroy(tmp_list);
00596 
00597   tmp_list = stp_color_list_parameters(v);
00598   stp_parameter_list_append(ret, tmp_list);
00599   stp_parameter_list_destroy(tmp_list);
00600 
00601   tmp_list = stp_dither_list_parameters(v);
00602   stp_parameter_list_append(ret, tmp_list);
00603   stp_parameter_list_destroy(tmp_list);
00604 
00605   tmp_list = stp_list_generic_parameters(v);
00606   stp_parameter_list_append(ret, tmp_list);
00607   stp_parameter_list_destroy(tmp_list);
00608 
00609   return ret;
00610 }
00611 
00612 void
00613 stp_abort(void)
00614 {
00615   abort();
00616 }

Generated on Wed May 12 20:21:33 2004 for libgimpprint API Reference by doxygen1.2.17