Example #1
0
/*
 * ... FIXME: docs
 */
static void
print_summary (struct jpeg_decompress_struct *cinfo,
               gint                           num_quant_tables)
{
  gint    quality;
  gint    i;
  GSList *source_list;

  /* detect JPEG quality - test the formula used in the jpeg plug-in */
  quality = jpeg_detect_quality (cinfo);
  if (quality > 0)
    g_print ("\tQuality:  %02d (exact)\n", quality);
  else if (quality < 0)
    g_print ("\tQuality:  %02d (approx)\n", -quality);
  else
    g_print ("\tQuality:  unknown\n");

  /* JPEG sampling factors */
  g_print ("\tSampling: %dx%d",
           cinfo->comp_info[0].h_samp_factor,
           cinfo->comp_info[0].v_samp_factor);
  if ((cinfo->num_components > 1 && cinfo->num_components != 3)
      || cinfo->comp_info[1].h_samp_factor != 1
      || cinfo->comp_info[1].v_samp_factor != 1
      || cinfo->comp_info[2].h_samp_factor != 1
      || cinfo->comp_info[2].v_samp_factor != 1)
    {
      for (i = 1; i < cinfo->num_components; i++)
        g_print (",%dx%d",
                 cinfo->comp_info[i].h_samp_factor,
                 cinfo->comp_info[i].v_samp_factor);
    }
  g_print ("\n");

  /* Number of quantization tables */
  g_print ("\tQ.tables: %d\n", num_quant_tables);

  source_list = detect_source (cinfo, num_quant_tables);
  if (source_list)
    {
      GSList  *l;
      guint32  hash;
      guint32  hash_t;

      hash = hash_quant_tables (cinfo);
      hash_t = hash_transposed_quant_tables (cinfo);

      for (l = source_list; l; l = l->next)
        {
          QuantInfo   *source_info = l->data;
          const gchar *comment = "";

          if (source_info->hash == hash)
            comment = "";
          else if (source_info->hash == hash_t)
            comment = " (rotated)";
          else if (num_quant_tables == 1)
            comment = " (grayscale)";
          else
            comment = " (FALSE MATCH)";

          g_print ("\tSource:   %s - %s%s\n",
                   source_info->source_name,
                   source_info->setting_name,
                   comment);
        }
      g_slist_free (source_list);
    }
  else
    g_print ("\tSource:   unknown\n");
}
Example #2
0
/**
 * jpeg_detect_original_settings:
 * @cinfo: a pointer to a JPEG decompressor info.
 * @image_ID: the image to which the parasite should be attached.
 *
 * Analyze the image being decompressed (@cinfo) and extract the
 * sampling factors, quantization tables and overall image quality.
 * Store this information in a parasite and attach it to @image_ID.
 *
 * This function must be called after jpeg_read_header() so that
 * @cinfo contains the quantization tables and the sampling factors
 * for each component.
 *
 * Return Value: TRUE if a parasite has been attached to @image_ID.
 */
gboolean
jpeg_detect_original_settings (struct jpeg_decompress_struct *cinfo,
                               gint32                         image_ID)
{
  guint         parasite_size;
  guchar       *parasite_data;
  GimpParasite *parasite;
  guchar       *dest;
  gint          quality;
  gint          num_quant_tables = 0;
  gint          t;
  gint          i;

  g_return_val_if_fail (cinfo != NULL, FALSE);
  if (cinfo->jpeg_color_space == JCS_UNKNOWN
      || cinfo->out_color_space == JCS_UNKNOWN)
    return FALSE;

  quality = jpeg_detect_quality (cinfo);
  /* no need to attach quantization tables if they are the ones from IJG */
  if (quality <= 0)
    {
      for (t = 0; t < 4; t++)
        if (cinfo->quant_tbl_ptrs[t])
          num_quant_tables++;
    }

  parasite_size = 4 + cinfo->num_components * 2 + num_quant_tables * 128;
  parasite_data = g_new (guchar, parasite_size);
  dest = parasite_data;

  *dest++ = CLAMP0255 (cinfo->jpeg_color_space);
  *dest++ = ABS (quality);
  *dest++ = CLAMP0255 (cinfo->num_components);
  *dest++ = num_quant_tables;

  for (i = 0; i < cinfo->num_components; i++)
    {
      *dest++ = CLAMP0255 (cinfo->comp_info[i].h_samp_factor);
      *dest++ = CLAMP0255 (cinfo->comp_info[i].v_samp_factor);
    }

  if (quality <= 0)
    {
      for (t = 0; t < 4; t++)
        if (cinfo->quant_tbl_ptrs[t])
          for (i = 0; i < DCTSIZE2; i++)
            {
              guint16 c = cinfo->quant_tbl_ptrs[t]->quantval[i];
              *dest++ = c / 256;
              *dest++ = c & 255;
            }
    }

  parasite = gimp_parasite_new ("jpeg-settings",
                                GIMP_PARASITE_PERSISTENT,
                                parasite_size,
                                parasite_data);
  g_free (parasite_data);
  gimp_image_parasite_attach (image_ID, parasite);
  gimp_parasite_free (parasite);
  return TRUE;
}
Example #3
0
static void
add_unknown_table (struct jpeg_decompress_struct *cinfo,
                   gchar                         *filename)
{
  guint32         hashval;
  GSList         *list;
  QuantTableData *table_data;
  gint            num_quant_tables;
  gint            t;
  gint            i;

  hashval = hash_quant_tables (cinfo);

  /* linear search - the number of unknown tables is usually very small */
  for (list = found_tables; list; list = list->next)
    {
      table_data = list->data;
      if (table_data->hashval == hashval
          && table_data->subsmp_h == cinfo->comp_info[0].h_samp_factor
          && table_data->subsmp_v == cinfo->comp_info[0].v_samp_factor)
        {
          /* this unknown table has already been seen in previous files */
          table_data->files = g_slist_prepend (table_data->files, filename);
          return;
        }
    }

  /* not found => new table */
  table_data = g_new (QuantTableData, 1);
  table_data->hashval = hashval;
  table_data->subsmp_h = cinfo->comp_info[0].h_samp_factor;
  table_data->subsmp_v = cinfo->comp_info[0].v_samp_factor;

  num_quant_tables = 0;
  for (t = 0; t < 4; t++)
    if (cinfo->quant_tbl_ptrs[t])
      num_quant_tables++;

  table_data->num_quant_tables = num_quant_tables;
  table_data->ijg_qual = jpeg_detect_quality (cinfo);
  table_data->files = g_slist_prepend (NULL, filename);

  if (cinfo->quant_tbl_ptrs[0])
    {
      for (i = 0; i < DCTSIZE2; i++)
        table_data->luminance[i] = cinfo->quant_tbl_ptrs[0]->quantval[i];
    }
  else
    {
      for (i = 0; i < DCTSIZE2; i++)
        table_data->luminance[i] = 0;
    }

  if (cinfo->quant_tbl_ptrs[1])
    {
      for (i = 0; i < DCTSIZE2; i++)
        table_data->chrominance[i] = cinfo->quant_tbl_ptrs[1]->quantval[i];
    }
  else
    {
      for (i = 0; i < DCTSIZE2; i++)
        table_data->chrominance[i] = 0;
    }

  found_tables = g_slist_prepend (found_tables, table_data);
}