gdkrgb.c

Go to the documentation of this file.
00001 /* GDK - The GIMP Drawing Kit
00002  * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
00003  *
00004  * This library is free software; you can redistribute it and/or
00005  * modify it under the terms of the GNU Library General Public
00006  * License as published by the Free Software Foundation; either
00007  * version 2 of the License, or (at your option) any later version.
00008  *
00009  * This library is distributed in the hope that it will be useful,
00010  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00011  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00012  * Library General Public License for more details.
00013  *
00014  * You should have received a copy of the GNU Library General Public
00015  * License along with this library; if not, write to the
00016  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00017  * Boston, MA 02111-1307, USA.
00018  */
00019 
00020 /* For more information on GdkRgb, see http://www.levien.com/gdkrgb/
00021 
00022    Raph Levien <raph@acm.org>
00023    */
00024 
00025 /*
00026  * Modified by the GTK+ Team and others 1997-1999.  See the AUTHORS
00027  * file for a list of people on the GTK+ Team.  See the ChangeLog
00028  * files for a list of changes.  These files are distributed with
00029  * GTK+ at ftp://ftp.gtk.org/pub/gtk/. 
00030  */
00031 
00032 #include <math.h>
00033 
00034 #if HAVE_CONFIG_H
00035 #  include <config.h>
00036 #  if STDC_HEADERS
00037 #    include <stdio.h>
00038 #    include <stdlib.h>
00039 #    include <string.h>
00040 #  endif
00041 #else
00042 #  include <stdio.h>
00043 #  include <stdlib.h>
00044 #endif
00045 
00046 
00047 #define ENABLE_GRAYSCALE
00048 
00049 #ifdef GDK_RGB_STANDALONE
00050 
00051 /* Compiling as a standalone module (i.e. with Gtk 1.0) */
00052 /* gtk/gtk.h is already included in gdkrgbstub.c */
00053 #include "config.h"
00054 #include <gdk/gdkprivate.h>
00055 
00056 #else
00057 
00058 /* Compiling as a part of Gtk 1.1 or later */
00059 #include "config.h"
00060 #include "gdkprivate.h"
00061 
00062 #endif
00063 
00064 #include "gdk.h"                /* For gdk_flush() */
00065 #include "gdkrgb.h"
00066 
00067 typedef struct _GdkRgbInfo GdkRgbInfo;
00068 
00069 typedef void (*GdkRgbConvFunc) (GdkImage * image,
00070                                 gint x0, gint y0,
00071                                 gint width, gint height,
00072                                 guchar * buf, int rowstride,
00073                                 gint x_align, gint y_align,
00074                                 GdkRgbCmap * cmap);
00075 
00076 static const gchar *visual_names[] = {
00077    "static gray",
00078    "grayscale",
00079    "static color",
00080    "pseudo color",
00081    "true color",
00082    "direct color",
00083 };
00084 
00085 /* Some of these fields should go, as they're not being used at all.
00086    Globals should generally migrate into here - it's very likely that
00087    we'll want to run more than one GdkRgbInfo context at the same time
00088    (i.e. some but not all windows have privately installed
00089    colormaps). */
00090 
00091 struct _GdkRgbInfo {
00092    GdkVisual *visual;
00093    GdkColormap *cmap;
00094 
00095    gulong *color_pixels;
00096    gulong *gray_pixels;
00097    gulong *reserved_pixels;
00098 
00099    guint nred_shades;
00100    guint ngreen_shades;
00101    guint nblue_shades;
00102    guint ngray_shades;
00103    guint nreserved;
00104 
00105    guint bpp;
00106    gint cmap_alloced;
00107    gdouble gamma;
00108 
00109    /* Generally, the stage buffer is used to convert 32bit RGB, gray,
00110       and indexed images into 24 bit packed RGB. */
00111    guchar *stage_buf;
00112 
00113    GdkRgbCmap *gray_cmap;
00114 
00115    gboolean dith_default;
00116 
00117    gboolean bitmap;             /* set true if in 1 bit per pixel mode */
00118    GdkGC *own_gc;
00119 
00120    /* Convert functions */
00121    GdkRgbConvFunc conv;
00122    GdkRgbConvFunc conv_d;
00123 
00124    GdkRgbConvFunc conv_32;
00125    GdkRgbConvFunc conv_32_d;
00126 
00127    GdkRgbConvFunc conv_gray;
00128    GdkRgbConvFunc conv_gray_d;
00129 
00130    GdkRgbConvFunc conv_indexed;
00131    GdkRgbConvFunc conv_indexed_d;
00132 };
00133 
00134 static gboolean gdk_rgb_install_cmap = FALSE;
00135 static gint gdk_rgb_min_colors = 5 * 5 * 5;
00136 static gboolean gdk_rgb_verbose = FALSE;
00137 
00138 #define IMAGE_WIDTH 256
00139 #define STAGE_ROWSTRIDE (IMAGE_WIDTH * 3)
00140 #define IMAGE_HEIGHT 64
00141 #define N_IMAGES 6
00142 
00143 static GdkRgbInfo *image_info = NULL;
00144 static GdkImage *static_image[N_IMAGES];
00145 static gint static_image_idx;
00146 
00147 static guchar *colorcube;
00148 static guchar *colorcube_d;
00149 
00150 static gint
00151 gdk_rgb_cmap_fail(const char *msg, GdkColormap * cmap, gulong * pixels)
00152 {
00153    gulong free_pixels[256];
00154    gint n_free;
00155    gint i;
00156 
00157 #ifdef VERBOSE
00158    g_print("%s", msg);
00159 #endif
00160    n_free = 0;
00161    for (i = 0; i < 256; i++)
00162       if (pixels[i] < 256)
00163          free_pixels[n_free++] = pixels[i];
00164    if (n_free)
00165       gdk_colors_free(cmap, free_pixels, n_free, 0);
00166    return 0;
00167 }
00168 
00169 static void
00170 gdk_rgb_make_colorcube(gulong * pixels, gint nr, gint ng, gint nb)
00171 {
00172    guchar rt[16], gt[16], bt[16];
00173    gint i;
00174 
00175    colorcube = g_new(guchar, 4096);
00176    for (i = 0; i < 16; i++) {
00177       rt[i] = ng * nb * ((i * 17 * (nr - 1) + 128) >> 8);
00178       gt[i] = nb * ((i * 17 * (ng - 1) + 128) >> 8);
00179       bt[i] = ((i * 17 * (nb - 1) + 128) >> 8);
00180    }
00181 
00182    for (i = 0; i < 4096; i++) {
00183       colorcube[i] =
00184           pixels[rt[i >> 8] + gt[(i >> 4) & 0x0f] + bt[i & 0x0f]];
00185 #ifdef VERBOSE
00186       g_print("%03x %02x %x %x %x\n", i, colorcube[i], rt[i >> 8],
00187               gt[(i >> 4) & 0x0f], bt[i & 0x0f]);
00188 #endif
00189    }
00190 }
00191 
00192 /* this is the colorcube suitable for dithering */
00193 static void
00194 gdk_rgb_make_colorcube_d(gulong * pixels, gint nr, gint ng, gint nb)
00195 {
00196    gint r, g, b;
00197    gint i;
00198 
00199    colorcube_d = g_new(guchar, 512);
00200    for (i = 0; i < 512; i++) {
00201       r = MIN(nr - 1, i >> 6);
00202       g = MIN(ng - 1, (i >> 3) & 7);
00203       b = MIN(nb - 1, i & 7);
00204       colorcube_d[i] = pixels[(r * ng + g) * nb + b];
00205    }
00206 }
00207 
00208 /* Try installing a color cube of the specified size.
00209    Make the colorcube and return TRUE on success */
00210 static gint gdk_rgb_try_colormap(gint nr, gint ng, gint nb)
00211 {
00212    gint r, g, b;
00213    gint ri, gi, bi;
00214    gint r0, g0, b0;
00215    GdkColormap *cmap;
00216    GdkColor color;
00217    gulong pixels[256];
00218    gulong junk[256];
00219    gint i;
00220    gint d2;
00221    gint colors_needed;
00222    gint idx;
00223    gint best[256];
00224 
00225    if (nr * ng * nb < gdk_rgb_min_colors)
00226       return FALSE;
00227 
00228    if (image_info->cmap_alloced)
00229       cmap = image_info->cmap;
00230    else
00231       cmap = gdk_colormap_get_system();
00232 
00233    colors_needed = nr * ng * nb;
00234    for (i = 0; i < 256; i++) {
00235       best[i] = 192;
00236       pixels[i] = 256;
00237    }
00238 
00239 #ifndef GAMMA
00240    if (!gdk_rgb_install_cmap)
00241       /* find color cube colors that are already present */
00242       for (i = 0; i < MIN(256, cmap->size); i++) {
00243          r = cmap->colors[i].red >> 8;
00244          g = cmap->colors[i].green >> 8;
00245          b = cmap->colors[i].blue >> 8;
00246          ri = (r * (nr - 1) + 128) >> 8;
00247          gi = (g * (ng - 1) + 128) >> 8;
00248          bi = (b * (nb - 1) + 128) >> 8;
00249          r0 = ri * 255 / (nr - 1);
00250          g0 = gi * 255 / (ng - 1);
00251          b0 = bi * 255 / (nb - 1);
00252          idx = ((ri * nr) + gi) * nb + bi;
00253          d2 = (r - r0) * (r - r0) + (g - g0) * (g - g0) + (b - b0) * (b -
00254                                                                       b0);
00255          if (d2 < best[idx]) {
00256             if (pixels[idx] < 256)
00257                gdk_colors_free(cmap, pixels + idx, 1, 0);
00258             else
00259                colors_needed--;
00260             color = cmap->colors[i];
00261             if (!gdk_color_alloc(cmap, &color))
00262                return gdk_rgb_cmap_fail("error allocating system color\n",
00263                                         cmap, pixels);
00264             pixels[idx] = color.pixel;  /* which is almost certainly i */
00265             best[idx] = d2;
00266          }
00267       }
00268 #endif
00269 
00270    if (colors_needed) {
00271       if (!gdk_colors_alloc(cmap, 0, NULL, 0, junk, colors_needed)) {
00272          char tmp_str[80];
00273 
00274          sprintf(tmp_str,
00275                  "%d %d %d colormap failed (in gdk_colors_alloc)\n",
00276                  nr, ng, nb);
00277          return gdk_rgb_cmap_fail(tmp_str, cmap, pixels);
00278       }
00279 
00280       gdk_colors_free(cmap, junk, colors_needed, 0);
00281    }
00282 
00283    for (r = 0, i = 0; r < nr; r++)
00284       for (g = 0; g < ng; g++)
00285          for (b = 0; b < nb; b++, i++) {
00286             if (pixels[i] == 256) {
00287                color.red = r * 65535 / (nr - 1);
00288                color.green = g * 65535 / (ng - 1);
00289                color.blue = b * 65535 / (nb - 1);
00290 
00291 #ifdef GAMMA
00292                color.red = 65535 * pow(color.red / 65535.0, 0.5);
00293                color.green = 65535 * pow(color.green / 65535.0, 0.5);
00294                color.blue = 65535 * pow(color.blue / 65535.0, 0.5);
00295 #endif
00296 
00297                /* This should be a raw XAllocColor call */
00298                if (!gdk_color_alloc(cmap, &color)) {
00299                   char tmp_str[80];
00300 
00301                   sprintf(tmp_str, "%d %d %d colormap failed\n",
00302                           nr, ng, nb);
00303                   return gdk_rgb_cmap_fail(tmp_str, cmap, pixels);
00304                }
00305                pixels[i] = color.pixel;
00306             }
00307 #ifdef VERBOSE
00308             g_print("%d: %lx\n", i, pixels[i]);
00309 #endif
00310          }
00311 
00312    image_info->nred_shades = nr;
00313    image_info->ngreen_shades = ng;
00314    image_info->nblue_shades = nb;
00315    gdk_rgb_make_colorcube(pixels, nr, ng, nb);
00316    gdk_rgb_make_colorcube_d(pixels, nr, ng, nb);
00317    return TRUE;
00318 }
00319 
00320 /* Return TRUE on success. */
00321 static gboolean gdk_rgb_do_colormaps(void)
00322 {
00323    static const gint sizes[][3] = {
00324       /*    { 6, 7, 6 }, */
00325       {6, 6, 6},
00326       {6, 6, 5},
00327       {6, 6, 4},
00328       {5, 5, 5},
00329       {5, 5, 4},
00330       {4, 4, 4},
00331       {4, 4, 3},
00332       {3, 3, 3},
00333       {2, 2, 2}
00334    };
00335    static const gint n_sizes = sizeof(sizes) / (3 * sizeof(gint));
00336    gint i;
00337 
00338    for (i = 0; i < n_sizes; i++)
00339       if (gdk_rgb_try_colormap(sizes[i][0], sizes[i][1], sizes[i][2]))
00340          return TRUE;
00341    return FALSE;
00342 }
00343 
00344 /* Make a 2 x 2 x 2 colorcube */
00345 static void gdk_rgb_colorcube_222(void)
00346 {
00347    int i;
00348    GdkColor color;
00349    GdkColormap *cmap;
00350 
00351    if (image_info->cmap_alloced)
00352       cmap = image_info->cmap;
00353    else
00354       cmap = gdk_colormap_get_system();
00355 
00356    colorcube_d = g_new(guchar, 512);
00357 
00358    for (i = 0; i < 8; i++) {
00359       color.red = ((i & 4) >> 2) * 65535;
00360       color.green = ((i & 2) >> 1) * 65535;
00361       color.blue = (i & 1) * 65535;
00362       gdk_color_alloc(cmap, &color);
00363       colorcube_d[((i & 4) << 4) | ((i & 2) << 2) | (i & 1)] = color.pixel;
00364    }
00365 }
00366 
00367 void gdk_rgb_set_verbose(gboolean verbose)
00368 {
00369    gdk_rgb_verbose = verbose;
00370 }
00371 
00372 void gdk_rgb_set_install(gboolean install)
00373 {
00374    gdk_rgb_install_cmap = install;
00375 }
00376 
00377 void gdk_rgb_set_min_colors(gint min_colors)
00378 {
00379    gdk_rgb_min_colors = min_colors;
00380 }
00381 
00382 /* Return a "score" based on the following criteria (in hex):
00383 
00384    x000 is the quality - 1 is 1bpp, 2 is 4bpp,
00385                          4 is 8bpp,
00386                          7 is 15bpp truecolor, 8 is 16bpp truecolor,
00387                          9 is 24bpp truecolor.
00388    0x00 is the speed - 1 is the normal case,
00389                        2 means faster than normal
00390    00x0 gets a point for being the system visual
00391    000x gets a point for being pseudocolor
00392 
00393    A caveat: in the 8bpp modes, being the system visual seems to be
00394    quite important. Thus, all of the 8bpp modes should be ranked at
00395    the same speed.
00396 */
00397 static guint32 gdk_rgb_score_visual(GdkVisual * visual)
00398 {
00399    guint32 quality, speed, sys, pseudo;
00400 
00401    quality = 0;
00402    speed = 1;
00403    sys = 0;
00404    if (visual->type == GDK_VISUAL_TRUE_COLOR ||
00405        visual->type == GDK_VISUAL_DIRECT_COLOR) {
00406       if (visual->depth == 24) {
00407          quality = 9;
00408          /* Should test for MSB visual here, and set speed if so. */
00409       } else if (visual->depth == 16)
00410          quality = 8;
00411       else if (visual->depth == 15)
00412          quality = 7;
00413       else if (visual->depth == 8)
00414          quality = 4;
00415    } else if (visual->type == GDK_VISUAL_PSEUDO_COLOR ||
00416               visual->type == GDK_VISUAL_STATIC_COLOR) {
00417       if (visual->depth == 8)
00418          quality = 4;
00419       else if (visual->depth == 4)
00420          quality = 2;
00421       else if (visual->depth == 1)
00422          quality = 1;
00423    } else if (visual->type == GDK_VISUAL_STATIC_GRAY
00424 #ifdef ENABLE_GRAYSCALE
00425               || visual->type == GDK_VISUAL_GRAYSCALE
00426 #endif
00427        ) {
00428       if (visual->depth == 8)
00429          quality = 4;
00430       else if (visual->depth == 4)
00431          quality = 2;
00432       else if (visual->depth == 1)
00433          quality = 1;
00434    }
00435 
00436    if (quality == 0)
00437       return 0;
00438 
00439    sys = (visual == gdk_visual_get_system());
00440 
00441    pseudo = (visual->type == GDK_VISUAL_PSEUDO_COLOR
00442              || visual->type == GDK_VISUAL_TRUE_COLOR);
00443 
00444    if (gdk_rgb_verbose)
00445       g_print("Visual type = %s, depth = %d, %x:%x:%x%s; score=%x\n",
00446               visual_names[visual->type],
00447               visual->depth,
00448               visual->red_mask,
00449               visual->green_mask,
00450               visual->blue_mask,
00451               sys ? " (system)" : "",
00452               (quality << 12) | (speed << 8) | (sys << 4) | pseudo);
00453 
00454    return (quality << 12) | (speed << 8) | (sys << 4) | pseudo;
00455 }
00456 
00457 static void gdk_rgb_choose_visual(void)
00458 {
00459    GList *visuals, *tmp_list;
00460    guint32 score, best_score;
00461    GdkVisual *visual, *best_visual;
00462 
00463    visuals = gdk_list_visuals();
00464    tmp_list = visuals;
00465 
00466    best_visual = tmp_list->data;
00467    best_score = gdk_rgb_score_visual(best_visual);
00468    tmp_list = tmp_list->next;
00469    while (tmp_list) {
00470       visual = tmp_list->data;
00471       score = gdk_rgb_score_visual(visual);
00472       if (score > best_score) {
00473          best_score = score;
00474          best_visual = visual;
00475       }
00476       tmp_list = tmp_list->next;
00477    }
00478 
00479    g_list_free(visuals);
00480 
00481    image_info->visual = best_visual;
00482 }
00483 
00484 static void gdk_rgb_select_conv(GdkImage * image);
00485 
00486 static void gdk_rgb_set_gray_cmap(GdkColormap * cmap)
00487 {
00488    gint i;
00489    GdkColor color;
00490    gint status;
00491    gulong pixels[256];
00492    gint r, g, b, gray;
00493 
00494    for (i = 0; i < 256; i++) {
00495       color.pixel = i;
00496       color.red = i * 257;
00497       color.green = i * 257;
00498       color.blue = i * 257;
00499       status = gdk_color_alloc(cmap, &color);
00500       pixels[i] = color.pixel;
00501 #ifdef VERBOSE
00502       g_print("allocating pixel %d, %x %x %x, result %d\n",
00503               color.pixel, color.red, color.green, color.blue, status);
00504 #endif
00505    }
00506 
00507    /* Now, we make fake colorcubes - we ultimately just use the pseudocolor
00508       methods. */
00509 
00510    colorcube = g_new(guchar, 4096);
00511 
00512    for (i = 0; i < 4096; i++) {
00513       r = (i >> 4) & 0xf0;
00514       r = r | r >> 4;
00515       g = i & 0xf0;
00516       g = g | g >> 4;
00517       b = (i << 4 & 0xf0);
00518       b = b | b >> 4;
00519       gray = (g + ((r + b) >> 1)) >> 1;
00520       colorcube[i] = pixels[gray];
00521    }
00522 }
00523 
00524 void gdk_rgb_init(void)
00525 {
00526    gint i;
00527    static const gint byte_order[1] = { 1 };
00528 
00529    /* check endian sanity */
00530 #if G_BYTE_ORDER == G_BIG_ENDIAN
00531    if (((char *) byte_order)[0] == 1)
00532       g_error
00533           ("gdk_rgb_init: compiled for big endian, but this is a little endian machine.\n\n");
00534 #else
00535    if (((char *) byte_order)[0] != 1)
00536       g_error
00537           ("gdk_rgb_init: compiled for little endian, but this is a big endian machine.\n\n");
00538 #endif
00539 
00540    if (image_info == NULL) {
00541       image_info = g_new0(GdkRgbInfo, 1);
00542 
00543       image_info->visual = NULL;
00544       image_info->cmap = NULL;
00545 
00546       image_info->color_pixels = NULL;
00547       image_info->gray_pixels = NULL;
00548       image_info->reserved_pixels = NULL;
00549 
00550       image_info->nred_shades = 6;
00551       image_info->ngreen_shades = 6;
00552       image_info->nblue_shades = 4;
00553       image_info->ngray_shades = 24;
00554       image_info->nreserved = 0;
00555 
00556       image_info->bpp = 0;
00557       image_info->cmap_alloced = FALSE;
00558       image_info->gamma = 1.0;
00559 
00560       image_info->stage_buf = NULL;
00561 
00562       image_info->own_gc = NULL;
00563 
00564       gdk_rgb_choose_visual();
00565 
00566       if ((image_info->visual->type == GDK_VISUAL_PSEUDO_COLOR ||
00567            image_info->visual->type == GDK_VISUAL_STATIC_COLOR) &&
00568           image_info->visual->depth < 8 &&
00569           image_info->visual->depth >= 3) {
00570          image_info->cmap = gdk_colormap_get_system();
00571          gdk_rgb_colorcube_222();
00572       } else if (image_info->visual->type == GDK_VISUAL_PSEUDO_COLOR) {
00573          if (gdk_rgb_install_cmap ||
00574              image_info->visual != gdk_visual_get_system()) {
00575             image_info->cmap = gdk_colormap_new(image_info->visual, FALSE);
00576             image_info->cmap_alloced = TRUE;
00577          }
00578          if (!gdk_rgb_do_colormaps()) {
00579             image_info->cmap = gdk_colormap_new(image_info->visual, FALSE);
00580             image_info->cmap_alloced = TRUE;
00581             gdk_rgb_do_colormaps();
00582          }
00583          if (gdk_rgb_verbose)
00584             g_print("color cube: %d x %d x %d\n",
00585                     image_info->nred_shades,
00586                     image_info->ngreen_shades, image_info->nblue_shades);
00587 
00588          if (!image_info->cmap_alloced)
00589             image_info->cmap = gdk_colormap_get_system();
00590       }
00591 #ifdef ENABLE_GRAYSCALE
00592       else if (image_info->visual->type == GDK_VISUAL_GRAYSCALE) {
00593          image_info->cmap = gdk_colormap_new(image_info->visual, FALSE);
00594          gdk_rgb_set_gray_cmap(image_info->cmap);
00595          image_info->cmap_alloced = TRUE;
00596       }
00597 #endif
00598       else {
00599          /* Always install colormap in direct color. */
00600          if (image_info->visual->type != GDK_VISUAL_DIRECT_COLOR &&
00601              image_info->visual == gdk_visual_get_system())
00602             image_info->cmap = gdk_colormap_get_system();
00603          else {
00604             image_info->cmap = gdk_colormap_new(image_info->visual, FALSE);
00605             image_info->cmap_alloced = TRUE;
00606          }
00607       }
00608 
00609       image_info->bitmap = (image_info->visual->depth == 1);
00610 
00611       for (i = 0; i < N_IMAGES; i++)
00612          if (image_info->bitmap)
00613             /* Use malloc() instead of g_malloc since X will free() this mem */
00614             static_image[i] = gdk_image_new_bitmap(image_info->visual,
00615                                                    (gpointer)
00616                                                    malloc(IMAGE_WIDTH *
00617                                                           IMAGE_HEIGHT >>
00618                                                           3), IMAGE_WIDTH,
00619                                                    IMAGE_HEIGHT);
00620          else
00621             static_image[i] = gdk_image_new(GDK_IMAGE_FASTEST,
00622                                             image_info->visual,
00623                                             IMAGE_WIDTH, IMAGE_HEIGHT);
00624 
00625       image_info->bpp = static_image[0]->bpp;
00626 
00627       gdk_rgb_select_conv(static_image[0]);
00628 
00629    }
00630 }
00631 
00632 /* convert an rgb value into an X pixel code */
00633 gulong gdk_rgb_xpixel_from_rgb(guint32 rgb)
00634 {
00635    gulong pixel = 0;
00636 
00637    if (image_info->bitmap) {
00638       return ((rgb & 0xff0000) >> 16) +
00639           ((rgb & 0xff00) >> 7) + (rgb & 0xff) > 510;
00640    } else if (image_info->visual->type == GDK_VISUAL_PSEUDO_COLOR)
00641       pixel = colorcube[((rgb & 0xf00000) >> 12) |
00642                         ((rgb & 0xf000) >> 8) | ((rgb & 0xf0) >> 4)];
00643    else if (image_info->visual->depth < 8 &&
00644             image_info->visual->type == GDK_VISUAL_STATIC_COLOR) {
00645       pixel = colorcube_d[((rgb & 0x800000) >> 17) |
00646                           ((rgb & 0x8000) >> 12) | ((rgb & 0x80) >> 7)];
00647    } else if (image_info->visual->type == GDK_VISUAL_TRUE_COLOR ||
00648               image_info->visual->type == GDK_VISUAL_DIRECT_COLOR) {
00649 #ifdef VERBOSE
00650       g_print("shift, prec: r %d %d g %d %d b %d %d\n",
00651               image_info->visual->red_shift,
00652               image_info->visual->red_prec,
00653               image_info->visual->green_shift,
00654               image_info->visual->green_prec,
00655               image_info->visual->blue_shift,
00656               image_info->visual->blue_prec);
00657 #endif
00658 
00659       pixel = (((((rgb & 0xff0000) >> 16) >>
00660                  (8 - image_info->visual->red_prec)) <<
00661                 image_info->visual->red_shift) +
00662                ((((rgb & 0xff00) >> 8) >>
00663                  (8 - image_info->visual->green_prec)) <<
00664                 image_info->visual->green_shift) +
00665                (((rgb & 0xff) >>
00666                  (8 - image_info->visual->blue_prec)) <<
00667                 image_info->visual->blue_shift));
00668    } else if (image_info->visual->type == GDK_VISUAL_STATIC_GRAY ||
00669               image_info->visual->type == GDK_VISUAL_GRAYSCALE) {
00670       int gray = ((rgb & 0xff0000) >> 16) +
00671           ((rgb & 0xff00) >> 7) + (rgb & 0xff);
00672 
00673       return gray >> (10 - image_info->visual->depth);
00674    }
00675 
00676    return pixel;
00677 }
00678 
00679 void gdk_rgb_gc_set_foreground(GdkGC * gc, guint32 rgb)
00680 {
00681    GdkColor color;
00682 
00683    color.pixel = gdk_rgb_xpixel_from_rgb(rgb);
00684    gdk_gc_set_foreground(gc, &color);
00685 }
00686 
00687 void gdk_rgb_gc_set_background(GdkGC * gc, guint32 rgb)
00688 {
00689    GdkColor color;
00690 
00691    color.pixel = gdk_rgb_xpixel_from_rgb(rgb);
00692    gdk_gc_set_background(gc, &color);
00693 }
00694 
00695 #if G_BYTE_ORDER == G_LITTLE_ENDIAN
00696 #define HAIRY_CONVERT_8
00697 #endif
00698 
00699 #ifdef HAIRY_CONVERT_8
00700 static void
00701 gdk_rgb_convert_8(GdkImage * image,
00702                   gint x0, gint y0, gint width, gint height,
00703                   guchar * buf, int rowstride,
00704                   gint x_align, gint y_align, GdkRgbCmap * cmap)
00705 {
00706    int x, y;
00707    gint bpl;
00708    guchar *obuf, *obptr;
00709    guchar *bptr, *bp2;
00710    gint r, g, b;
00711 
00712    bptr = buf;
00713    bpl = image->bpl;
00714    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
00715    for (y = 0; y < height; y++) {
00716       bp2 = bptr;
00717       obptr = obuf;
00718       if (((unsigned long) obuf | (unsigned long) bp2) & 3) {
00719          for (x = 0; x < width; x++) {
00720             r = *bp2++;
00721             g = *bp2++;
00722             b = *bp2++;
00723             obptr[0] = colorcube[((r & 0xf0) << 4) |
00724                                  (g & 0xf0) | (b >> 4)];
00725             obptr++;
00726          }
00727       } else {
00728          for (x = 0; x < width - 3; x += 4) {
00729             guint32 r1b0g0r0;
00730             guint32 g2r2b1g1;
00731             guint32 b3g3r3b2;
00732 
00733             r1b0g0r0 = ((guint32 *) bp2)[0];
00734             g2r2b1g1 = ((guint32 *) bp2)[1];
00735             b3g3r3b2 = ((guint32 *) bp2)[2];
00736             ((guint32 *) obptr)[0] =
00737                 colorcube[((r1b0g0r0 & 0xf0) << 4) |
00738                           ((r1b0g0r0 & 0xf000) >> 8) |
00739                           ((r1b0g0r0 & 0xf00000) >> 20)] |
00740                 (colorcube[((r1b0g0r0 & 0xf0000000) >> 20) |
00741                            (g2r2b1g1 & 0xf0) |
00742                            ((g2r2b1g1 & 0xf000) >> 12)] << 8) |
00743                 (colorcube[((g2r2b1g1 & 0xf00000) >> 12) |
00744                            ((g2r2b1g1 & 0xf0000000) >> 24) |
00745                            ((b3g3r3b2 & 0xf0) >> 4)] << 16) |
00746                 (colorcube[((b3g3r3b2 & 0xf000) >> 4) |
00747                            ((b3g3r3b2 & 0xf00000) >> 16) |
00748                            (b3g3r3b2 >> 28)] << 24);
00749             bp2 += 12;
00750             obptr += 4;
00751          }
00752          for (; x < width; x++) {
00753             r = *bp2++;
00754             g = *bp2++;
00755             b = *bp2++;
00756             obptr[0] = colorcube[((r & 0xf0) << 4) |
00757                                  (g & 0xf0) | (b >> 4)];
00758             obptr++;
00759          }
00760       }
00761       bptr += rowstride;
00762       obuf += bpl;
00763    }
00764 }
00765 #else
00766 static void
00767 gdk_rgb_convert_8(GdkImage * image,
00768                   gint x0, gint y0, gint width, gint height,
00769                   guchar * buf, int rowstride,
00770                   gint x_align, gint y_align, GdkRgbCmap * cmap)
00771 {
00772    int x, y;
00773    gint bpl;
00774    guchar *obuf, *obptr;
00775    guchar *bptr, *bp2;
00776    gint r, g, b;
00777 
00778    bptr = buf;
00779    bpl = image->bpl;
00780    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
00781    for (y = 0; y < height; y++) {
00782       bp2 = bptr;
00783       obptr = obuf;
00784       for (x = 0; x < width; x++) {
00785          r = *bp2++;
00786          g = *bp2++;
00787          b = *bp2++;
00788          obptr[0] = colorcube[((r & 0xf0) << 4) | (g & 0xf0) | (b >> 4)];
00789          obptr++;
00790       }
00791       bptr += rowstride;
00792       obuf += bpl;
00793    }
00794 }
00795 #endif
00796 
00797 #if 1
00798 
00799 /* This dither table was generated by Raph Levien using patented
00800    technology (US Patent 5,276,535). The dither table itself is in the
00801    public domain. */
00802 
00803 #define DM_WIDTH 128
00804 #define DM_WIDTH_SHIFT 7
00805 #define DM_HEIGHT 128
00806 static const guchar DM[128][128] = {
00807    {0, 41, 23, 5, 17, 39, 7, 15, 62, 23, 40, 51, 31, 47, 9, 32, 52, 27, 57,
00808     25, 6, 61, 27, 52, 37, 7, 40, 63, 18, 36, 10, 42, 25, 62, 45, 34, 20,
00809     42, 37, 14, 35, 29, 50, 10, 61, 2, 40, 8, 37, 12, 58, 22, 5, 41, 10,
00810     39, 0, 60, 11, 46, 2, 55, 38, 17, 36, 59, 13, 54, 37, 56, 8, 29, 16,
00811     13, 63, 22, 41, 55, 7, 20, 49, 14, 23, 55, 37, 23, 19, 36, 15, 49, 23,
00812     63, 30, 14, 38, 27, 53, 13, 22, 41, 19, 31, 7, 19, 50, 30, 49, 16, 3,
00813     32, 56, 40, 29, 34, 8, 48, 19, 45, 4, 51, 12, 46, 35, 49, 16, 42, 12,
00814     62},
00815    {30, 57, 36, 54, 47, 34, 52, 27, 43, 4, 28, 7, 17, 36, 62, 13, 44, 7,
00816     18, 48, 33, 21, 44, 14, 30, 47, 12, 33, 5, 55, 31, 58, 13, 30, 4, 17,
00817     52, 10, 60, 26, 46, 0, 39, 27, 42, 22, 47, 25, 60, 32, 9, 38, 48, 17,
00818     59, 30, 49, 18, 34, 25, 51, 19, 5, 48, 21, 8, 28, 46, 1, 32, 41, 19,
00819     54, 47, 37, 18, 28, 11, 44, 30, 39, 56, 2, 33, 8, 42, 61, 28, 58, 8,
00820     46, 9, 41, 4, 58, 7, 21, 48, 59, 10, 52, 14, 42, 57, 12, 25, 7, 53, 42,
00821     24, 11, 50, 17, 59, 42, 2, 36, 60, 32, 17, 63, 29, 21, 7, 59, 32, 24,
00822     39},
00823    {22, 8, 16, 32, 3, 25, 13, 57, 18, 45, 58, 39, 55, 20, 5, 42, 23, 34,
00824     63, 1, 51, 10, 58, 4, 60, 23, 53, 27, 44, 21, 3, 48, 8, 50, 43, 54, 27,
00825     32, 5, 55, 21, 58, 12, 53, 6, 36, 14, 50, 17, 29, 53, 15, 24, 52, 7,
00826     36, 13, 42, 4, 53, 9, 35, 61, 26, 56, 32, 49, 15, 62, 23, 6, 60, 2, 31,
00827     4, 48, 58, 38, 15, 61, 5, 25, 47, 28, 50, 15, 7, 40, 3, 32, 33, 52, 25,
00828     50, 35, 42, 61, 3, 28, 36, 23, 63, 4, 33, 46, 62, 36, 23, 60, 6, 54,
00829     28, 4, 37, 23, 55, 25, 8, 42, 54, 14, 6, 56, 38, 19, 52, 4, 46},
00830    {48, 53, 43, 12, 45, 63, 30, 37, 9, 34, 21, 1, 25, 47, 29, 58, 3, 54,
00831     15, 39, 29, 17, 38, 35, 20, 43, 1, 49, 15, 59, 29, 39, 22, 35, 16, 23,
00832     1, 47, 39, 18, 8, 44, 25, 31, 57, 19, 63, 4, 45, 3, 42, 61, 1, 31, 45,
00833     20, 57, 29, 62, 21, 32, 41, 14, 44, 3, 39, 5, 34, 10, 43, 51, 35, 23,
00834     52, 40, 10, 21, 1, 53, 18, 51, 43, 12, 62, 18, 54, 26, 51, 20, 57, 14,
00835     1, 62, 16, 11, 18, 32, 39, 17, 44, 1, 48, 26, 37, 18, 2, 51, 14, 28,
00836     45, 35, 18, 57, 13, 47, 11, 51, 20, 2, 39, 31, 47, 25, 1, 50, 11, 60,
00837     7},
00838    {18, 28, 1, 56, 21, 10, 51, 2, 46, 54, 14, 61, 11, 50, 13, 38, 19, 31,
00839     45, 9, 55, 24, 47, 5, 54, 9, 62, 11, 35, 8, 51, 14, 57, 6, 63, 40, 58,
00840     14, 51, 28, 62, 34, 15, 48, 1, 41, 30, 35, 55, 21, 34, 11, 49, 37, 8,
00841     52, 4, 23, 15, 43, 1, 58, 11, 23, 53, 16, 55, 26, 58, 18, 27, 12, 45,
00842     14, 25, 63, 42, 33, 27, 35, 9, 31, 21, 38, 1, 44, 34, 12, 48, 38, 21,
00843     44, 29, 47, 26, 53, 1, 46, 54, 8, 59, 29, 11, 55, 22, 41, 33, 20, 39,
00844     1, 48, 9, 44, 32, 5, 62, 29, 44, 57, 23, 10, 58, 34, 43, 15, 37, 26,
00845     33},
00846    {51, 38, 59, 24, 35, 42, 19, 60, 5, 32, 41, 26, 43, 33, 7, 53, 48, 11,
00847     59, 23, 42, 2, 61, 30, 16, 40, 32, 24, 56, 41, 19, 33, 37, 26, 47, 9,
00848     31, 22, 2, 45, 9, 54, 4, 37, 21, 52, 11, 23, 7, 57, 16, 25, 55, 18, 63,
00849     27, 46, 39, 56, 10, 50, 37, 29, 47, 19, 63, 24, 9, 46, 2, 39, 60, 9,
00850     57, 30, 7, 49, 11, 59, 3, 45, 57, 5, 60, 29, 22, 5, 60, 30, 9, 59, 18,
00851     40, 6, 57, 36, 30, 12, 24, 34, 15, 40, 52, 6, 49, 9, 58, 4, 63, 12, 26,
00852     61, 22, 53, 38, 16, 35, 14, 28, 50, 42, 17, 5, 28, 62, 20, 54, 12},
00853    {26, 6, 31, 15, 49, 6, 38, 27, 22, 49, 16, 56, 2, 62, 30, 21, 0, 36, 28,
00854     6, 49, 32, 13, 52, 26, 50, 19, 46, 3, 26, 62, 0, 53, 12, 29, 3, 53, 41,
00855     60, 24, 38, 13, 58, 16, 43, 9, 59, 39, 46, 28, 44, 40, 2, 33, 13, 41,
00856     16, 6, 47, 31, 26, 17, 57, 6, 38, 0, 42, 36, 29, 52, 20, 31, 48, 0, 34,
00857     56, 20, 36, 23, 54, 14, 41, 24, 37, 10, 55, 46, 25, 16, 45, 36, 4, 55,
00858     23, 15, 8, 50, 62, 5, 56, 44, 20, 13, 28, 59, 31, 24, 47, 31, 52, 37,
00859     17, 40, 0, 26, 49, 3, 60, 7, 33, 0, 61, 53, 40, 8, 45, 2, 41},
00860    {16, 63, 43, 4, 61, 24, 56, 13, 53, 8, 36, 12, 24, 41, 16, 46, 60, 26,
00861     52, 39, 14, 57, 21, 37, 0, 45, 7, 59, 38, 17, 43, 10, 45, 20, 61, 43,
00862     19, 11, 33, 17, 50, 32, 23, 61, 28, 49, 26, 0, 18, 51, 5, 60, 22, 58,
00863     29, 0, 59, 34, 19, 62, 3, 52, 7, 44, 30, 59, 13, 50, 15, 62, 7, 17, 38,
00864     22, 44, 15, 40, 4, 47, 28, 33, 17, 49, 16, 51, 40, 10, 56, 0, 53, 13,
00865     49, 28, 38, 60, 21, 43, 19, 37, 27, 3, 51, 34, 39, 0, 45, 15, 43, 10,
00866     21, 3, 55, 8, 33, 59, 10, 41, 18, 52, 24, 46, 20, 30, 13, 58, 22, 36,
00867     57},
00868    {50, 34, 11, 47, 29, 17, 44, 0, 33, 63, 28, 46, 52, 5, 57, 10, 42, 18,
00869     4, 63, 20, 8, 44, 10, 56, 34, 14, 29, 5, 54, 23, 59, 32, 49, 7, 34, 49,
00870     27, 56, 0, 42, 7, 46, 3, 40, 6, 54, 32, 62, 13, 36, 10, 47, 8, 35, 49,
00871     24, 51, 12, 40, 22, 35, 60, 12, 22, 51, 33, 4, 40, 25, 43, 55, 5, 54,
00872     12, 61, 26, 51, 8, 62, 0, 53, 7, 63, 2, 32, 19, 34, 42, 24, 31, 63, 2,
00873     10, 45, 33, 0, 48, 9, 61, 22, 47, 8, 62, 18, 56, 7, 54, 27, 57, 46, 30,
00874     50, 19, 45, 30, 56, 36, 22, 47, 11, 38, 3, 51, 32, 48, 18, 9},
00875    {0, 21, 40, 19, 52, 9, 37, 48, 20, 40, 3, 18, 27, 38, 35, 22, 31, 56,
00876     13, 35, 46, 28, 60, 40, 27, 18, 61, 50, 41, 30, 7, 36, 2, 25, 16, 57,
00877     5, 15, 47, 29, 55, 19, 30, 52, 15, 34, 20, 12, 43, 30, 20, 54, 25, 44,
00878     53, 12, 38, 5, 55, 27, 48, 15, 33, 27, 45, 8, 19, 28, 56, 11, 33, 49,
00879     18, 36, 29, 2, 45, 16, 39, 19, 31, 43, 27, 35, 20, 52, 26, 6, 61, 11,
00880     41, 17, 29, 51, 20, 56, 25, 32, 41, 17, 53, 31, 25, 14, 42, 23, 35, 16,
00881     38, 6, 34, 12, 15, 62, 6, 21, 13, 1, 63, 9, 55, 27, 43, 25, 14, 4, 31,
00882     55},
00883    {44, 29, 61, 2, 35, 58, 26, 15, 60, 10, 51, 59, 14, 55, 8, 50, 2, 44,
00884     25, 51, 1, 33, 16, 4, 48, 36, 2, 21, 12, 57, 48, 13, 51, 55, 40, 28,
00885     37, 62, 8, 39, 12, 63, 36, 10, 59, 24, 56, 47, 9, 50, 41, 1, 32, 17, 6,
00886     21, 61, 30, 9, 43, 1, 54, 41, 2, 54, 37, 48, 61, 1, 46, 21, 3, 58, 24,
00887     50, 32, 60, 10, 57, 25, 46, 12, 59, 4, 45, 13, 57, 47, 27, 39, 5, 58,
00888     47, 14, 35, 4, 52, 13, 60, 6, 36, 10, 45, 55, 4, 50, 29, 2, 61, 50, 25,
00889     58, 44, 24, 36, 42, 54, 28, 40, 32, 16, 56, 6, 62, 46, 39, 60, 23},
00890    {7, 48, 14, 54, 23, 40, 4, 45, 30, 22, 42, 32, 1, 44, 20, 29, 58, 8, 37,
00891     19, 41, 54, 24, 58, 9, 53, 25, 46, 34, 16, 23, 38, 27, 11, 18, 1, 52,
00892     21, 35, 22, 48, 5, 25, 45, 18, 38, 2, 27, 35, 4, 57, 15, 62, 39, 57,
00893     28, 42, 16, 36, 60, 24, 18, 10, 63, 20, 5, 16, 23, 37, 14, 59, 27, 41,
00894     8, 13, 42, 21, 35, 6, 50, 3, 38, 15, 48, 30, 39, 17, 3, 49, 14, 53, 33,
00895     24, 7, 61, 44, 11, 39, 23, 49, 19, 58, 1, 32, 36, 12, 60, 41, 20, 13,
00896     41, 4, 39, 1, 48, 8, 18, 51, 14, 44, 5, 37, 21, 34, 1, 26, 10, 37},
00897    {53, 36, 27, 9, 50, 12, 32, 55, 2, 57, 7, 17, 48, 34, 63, 15, 40, 26,
00898     62, 11, 49, 6, 31, 39, 22, 42, 6, 63, 1, 39, 60, 4, 42, 61, 32, 45, 24,
00899     44, 2, 60, 16, 41, 53, 1, 33, 61, 49, 17, 63, 23, 45, 26, 33, 3, 23,
00900     46, 2, 50, 20, 4, 45, 34, 49, 30, 39, 58, 44, 31, 53, 34, 6, 52, 30,
00901     47, 63, 1, 53, 22, 42, 31, 58, 23, 54, 22, 61, 8, 36, 59, 22, 35, 21,
00902     1, 55, 40, 27, 16, 30, 54, 2, 29, 43, 16, 39, 63, 21, 46, 26, 10, 48,
00903     32, 19, 53, 30, 56, 26, 60, 33, 4, 61, 23, 49, 59, 15, 53, 19, 58, 42,
00904     16},
00905    {20, 5, 59, 46, 25, 62, 7, 19, 43, 25, 37, 61, 11, 24, 4, 54, 12, 52, 3,
00906     32, 17, 61, 12, 47, 15, 55, 18, 31, 53, 28, 9, 50, 21, 6, 55, 9, 58,
00907     14, 54, 26, 33, 7, 31, 58, 13, 21, 8, 42, 29, 6, 37, 11, 48, 52, 14,
00908     60, 11, 39, 56, 32, 14, 58, 7, 26, 17, 4, 42, 8, 11, 47, 19, 38, 10,
00909     17, 26, 37, 9, 55, 28, 13, 18, 40, 6, 33, 1, 43, 25, 11, 51, 7, 62, 43,
00910     18, 37, 3, 57, 45, 9, 38, 58, 5, 52, 27, 7, 17, 53, 5, 57, 37, 2, 63,
00911     9, 22, 15, 11, 38, 25, 45, 35, 0, 28, 10, 41, 30, 50, 8, 31, 57},
00912    {49, 33, 16, 38, 1, 42, 51, 34, 53, 14, 28, 49, 30, 56, 36, 23, 43, 20,
00913     38, 56, 22, 45, 28, 0, 62, 35, 26, 44, 11, 19, 52, 35, 44, 15, 30, 38,
00914     10, 31, 40, 4, 46, 50, 20, 40, 27, 44, 51, 14, 56, 53, 19, 59, 7, 29,
00915     41, 19, 35, 25, 8, 52, 22, 44, 13, 53, 50, 32, 61, 24, 56, 25, 63, 0,
00916     45, 57, 33, 59, 16, 46, 4, 62, 50, 11, 60, 37, 52, 19, 55, 29, 37, 46,
00917     13, 26, 48, 10, 50, 34, 21, 63, 26, 13, 42, 33, 22, 55, 35, 28, 43, 15,
00918     24, 51, 27, 34, 46, 49, 58, 3, 52, 9, 57, 19, 48, 55, 3, 35, 12, 45,
00919     24, 3},
00920    {41, 11, 56, 28, 18, 31, 22, 10, 37, 6, 47, 13, 3, 41, 9, 46, 0, 48, 29,
00921     6, 34, 10, 55, 37, 20, 8, 49, 3, 41, 59, 14, 25, 0, 63, 19, 47, 27, 51,
00922     17, 57, 23, 10, 61, 6, 54, 3, 38, 31, 0, 22, 34, 43, 20, 55, 31, 0, 49,
00923     63, 29, 38, 3, 62, 28, 40, 0, 22, 14, 35, 2, 48, 15, 43, 23, 14, 3, 29,
00924     49, 20, 39, 34, 0, 44, 29, 9, 15, 47, 5, 42, 0, 31, 58, 5, 31, 61, 23,
00925     15, 0, 47, 19, 50, 24, 3, 59, 11, 44, 0, 31, 59, 6, 42, 17, 60, 0, 39,
00926     20, 31, 43, 17, 29, 40, 12, 25, 60, 22, 52, 15, 63, 29},
00927    {20, 52, 8, 44, 62, 4, 59, 49, 17, 63, 21, 39, 60, 18, 52, 27, 33, 59,
00928     14, 51, 59, 43, 24, 5, 51, 30, 57, 17, 32, 5, 37, 56, 48, 34, 42, 3,
00929     60, 5, 36, 13, 43, 37, 18, 34, 25, 12, 59, 24, 47, 36, 11, 50, 3, 38,
00930     9, 58, 16, 5, 43, 18, 47, 10, 37, 18, 59, 46, 29, 52, 40, 12, 34, 28,
00931     56, 36, 53, 7, 43, 8, 24, 52, 26, 17, 56, 43, 24, 32, 63, 20, 57, 16,
00932     22, 52, 36, 8, 41, 56, 29, 32, 54, 7, 35, 57, 14, 48, 20, 62, 13, 39,
00933     53, 29, 8, 45, 13, 29, 7, 61, 14, 54, 6, 63, 38, 32, 18, 43, 2, 39, 6,
00934     47},
00935    {0, 58, 23, 35, 13, 46, 12, 39, 0, 31, 55, 24, 5, 35, 15, 61, 17, 5, 39,
00936     25, 18, 2, 50, 33, 41, 13, 39, 23, 62, 46, 29, 12, 22, 8, 56, 25, 20,
00937     49, 32, 62, 0, 56, 11, 46, 63, 42, 9, 16, 55, 5, 60, 15, 62, 26, 45,
00938     21, 36, 51, 13, 57, 31, 24, 55, 6, 35, 9, 57, 5, 20, 60, 7, 51, 5, 19,
00939     40, 25, 61, 32, 56, 12, 36, 48, 21, 2, 58, 12, 39, 28, 9, 50, 40, 12,
00940     44, 18, 25, 49, 6, 38, 11, 62, 18, 46, 30, 9, 40, 25, 49, 19, 10, 36,
00941     55, 22, 33, 52, 41, 18, 37, 27, 49, 21, 2, 46, 7, 53, 33, 61, 27, 35},
00942    {41, 31, 5, 39, 51, 26, 33, 57, 27, 41, 9, 44, 54, 29, 48, 7, 44, 36,
00943     57, 10, 31, 63, 16, 45, 11, 60, 1, 47, 7, 20, 43, 3, 58, 36, 13, 52,
00944     39, 7, 15, 28, 22, 48, 30, 21, 1, 29, 49, 44, 27, 17, 40, 30, 24, 42,
00945     12, 53, 33, 7, 47, 20, 1, 42, 11, 49, 25, 43, 17, 32, 45, 27, 41, 21,
00946     31, 62, 11, 49, 2, 15, 42, 5, 63, 7, 41, 27, 49, 6, 54, 23, 46, 34, 2,
00947     28, 54, 3, 59, 12, 46, 17, 42, 28, 40, 1, 37, 51, 5, 55, 2, 34, 47, 16,
00948     3, 62, 47, 5, 23, 56, 1, 44, 12, 34, 51, 16, 57, 11, 25, 17, 54, 13},
00949    {60, 26, 55, 18, 3, 60, 20, 6, 52, 15, 50, 19, 32, 11, 23, 53, 26, 21,
00950     1, 47, 42, 27, 8, 58, 21, 27, 53, 36, 26, 54, 31, 50, 17, 30, 45, 1,
00951     29, 59, 44, 53, 41, 4, 35, 58, 51, 19, 32, 4, 52, 34, 48, 8, 51, 5, 56,
00952     2, 25, 61, 27, 38, 54, 27, 62, 21, 51, 1, 39, 62, 10, 50, 1, 58, 13,
00953     47, 38, 18, 35, 54, 22, 51, 30, 19, 59, 34, 14, 32, 44, 4, 60, 15, 52,
00954     62, 20, 43, 30, 35, 21, 60, 4, 52, 12, 24, 61, 18, 30, 42, 23, 61, 25,
00955     50, 27, 38, 11, 59, 12, 35, 50, 30, 59, 24, 8, 42, 28, 37, 48, 9, 44,
00956     21},
00957    {10, 47, 15, 50, 30, 43, 8, 45, 29, 2, 36, 59, 1, 58, 41, 3, 63, 31, 54,
00958     20, 13, 55, 35, 38, 4, 44, 15, 9, 61, 2, 14, 38, 61, 10, 23, 54, 18,
00959     12, 24, 2, 14, 55, 16, 8, 38, 14, 41, 60, 10, 23, 1, 58, 32, 17, 28,
00960     37, 41, 15, 3, 60, 15, 33, 4, 36, 16, 59, 28, 14, 23, 55, 37, 18, 44,
00961     28, 2, 57, 30, 10, 27, 46, 14, 38, 3, 53, 21, 61, 17, 35, 10, 41, 26,
00962     7, 33, 9, 57, 1, 53, 37, 26, 20, 56, 48, 9, 33, 58, 16, 37, 7, 45, 1,
00963     57, 15, 32, 26, 42, 23, 7, 20, 4, 54, 31, 62, 22, 1, 59, 30, 4, 51},
00964    {36, 2, 38, 11, 24, 36, 54, 22, 62, 47, 25, 8, 28, 45, 16, 38, 12, 43,
00965     9, 37, 49, 3, 23, 52, 18, 30, 50, 33, 19, 42, 49, 26, 6, 40, 47, 35,
00966     63, 38, 50, 33, 60, 26, 36, 47, 24, 57, 6, 26, 39, 63, 19, 44, 14, 46,
00967     61, 9, 50, 30, 45, 23, 10, 50, 44, 8, 31, 54, 6, 46, 36, 4, 30, 54, 8,
00968     52, 22, 41, 4, 60, 40, 0, 58, 24, 45, 10, 37, 1, 48, 30, 56, 17, 38,
00969     48, 24, 47, 19, 39, 14, 8, 45, 32, 2, 34, 27, 44, 4, 52, 11, 56, 31,
00970     21, 40, 19, 44, 51, 2, 63, 46, 58, 36, 43, 14, 5, 50, 38, 14, 56, 40,
00971     23},
00972    {61, 46, 32, 63, 54, 1, 14, 34, 12, 40, 18, 49, 37, 10, 61, 30, 51, 24,
00973     60, 7, 29, 40, 62, 11, 46, 58, 6, 56, 24, 10, 34, 52, 21, 59, 16, 3,
00974     27, 5, 20, 46, 9, 40, 7, 62, 2, 30, 53, 15, 48, 10, 28, 35, 54, 6, 21,
00975     34, 18, 55, 7, 40, 57, 19, 26, 60, 41, 13, 24, 51, 19, 61, 9, 25, 34,
00976     15, 63, 11, 45, 17, 20, 47, 33, 8, 31, 62, 43, 26, 53, 7, 24, 59, 0,
00977     13, 55, 4, 62, 27, 51, 31, 63, 15, 58, 7, 54, 14, 46, 22, 28, 43, 12,
00978     63, 8, 54, 5, 17, 39, 33, 15, 10, 27, 17, 47, 34, 19, 45, 27, 12, 33,
00979     17},
00980    {5, 28, 21, 7, 17, 48, 42, 58, 23, 4, 63, 14, 55, 21, 34, 5, 19, 0, 45,
00981     17, 52, 15, 25, 32, 0, 22, 40, 13, 45, 62, 18, 0, 43, 11, 33, 55, 30,
00982     42, 57, 19, 51, 31, 22, 43, 18, 45, 34, 0, 43, 31, 56, 3, 23, 40, 59,
00983     0, 44, 13, 48, 35, 2, 32, 46, 0, 21, 48, 35, 3, 40, 32, 43, 59, 0, 48,
00984     33, 26, 53, 36, 55, 12, 51, 16, 55, 5, 18, 29, 11, 39, 51, 19, 45, 31,
00985     42, 21, 35, 6, 22, 47, 10, 38, 23, 50, 20, 36, 0, 60, 38, 4, 50, 35,
00986     48, 34, 24, 57, 9, 53, 28, 48, 61, 0, 56, 24, 53, 3, 63, 6, 42, 57},
00987    {13, 53, 45, 40, 58, 27, 6, 16, 38, 51, 33, 30, 43, 2, 47, 56, 40, 50,
00988     33, 57, 27, 5, 47, 42, 60, 36, 16, 54, 28, 4, 37, 57, 28, 51, 22, 8,
00989     45, 14, 6, 39, 0, 54, 11, 59, 28, 12, 50, 21, 61, 13, 19, 38, 49, 11,
00990     25, 37, 58, 29, 22, 63, 14, 56, 12, 53, 30, 63, 9, 57, 26, 12, 47, 16,
00991     23, 39, 50, 6, 31, 2, 25, 6, 28, 41, 36, 22, 50, 57, 42, 3, 34, 8, 28,
00992     61, 11, 50, 16, 54, 41, 0, 55, 43, 5, 29, 41, 63, 25, 16, 53, 18, 26,
00993     10, 21, 0, 61, 30, 41, 22, 3, 38, 20, 39, 29, 8, 41, 16, 36, 52, 22,
00994     19},
00995    {55, 34, 0, 25, 10, 32, 56, 44, 28, 0, 57, 7, 26, 53, 23, 8, 13, 35, 22,
00996     12, 36, 60, 20, 8, 14, 29, 48, 2, 41, 49, 23, 13, 39, 7, 48, 58, 25,
00997     53, 34, 62, 28, 16, 48, 4, 37, 56, 27, 5, 36, 52, 46, 7, 62, 33, 52,
00998     11, 17, 53, 5, 28, 41, 24, 38, 17, 5, 39, 20, 45, 15, 56, 5, 38, 60, 8,
00999     14, 57, 21, 48, 62, 39, 59, 13, 1, 60, 9, 32, 16, 63, 44, 25, 52, 15,
01000     36, 2, 60, 29, 12, 33, 25, 17, 59, 45, 13, 8, 49, 32, 6, 40, 59, 29,
01001     45, 37, 13, 47, 6, 55, 30, 45, 9, 52, 13, 59, 25, 47, 32, 1, 49, 30},
01002    {9, 39, 14, 61, 49, 37, 3, 20, 50, 13, 41, 19, 46, 17, 38, 59, 28, 62,
01003     4, 44, 54, 1, 34, 51, 55, 7, 63, 32, 21, 8, 56, 31, 62, 19, 36, 1, 41,
01004     17, 24, 12, 42, 35, 25, 52, 20, 8, 44, 59, 25, 2, 22, 42, 16, 29, 4,
01005     46, 20, 36, 43, 9, 51, 8, 49, 26, 58, 33, 54, 1, 37, 29, 52, 20, 27,
01006     45, 19, 35, 42, 16, 10, 32, 20, 49, 46, 27, 40, 4, 47, 22, 13, 55, 4,
01007     47, 26, 44, 23, 40, 58, 19, 48, 13, 31, 2, 57, 34, 42, 19, 61, 32, 14,
01008     55, 5, 51, 26, 19, 58, 16, 49, 14, 62, 5, 33, 44, 21, 7, 60, 26, 11,
01009     41},
01010    {62, 24, 47, 29, 8, 19, 53, 11, 60, 24, 32, 61, 4, 55, 31, 2, 49, 16,
01011     39, 9, 31, 24, 43, 17, 26, 38, 11, 25, 58, 43, 12, 35, 3, 46, 15, 32,
01012     63, 4, 49, 56, 2, 60, 10, 32, 63, 17, 39, 12, 55, 30, 57, 9, 48, 55,
01013     39, 24, 60, 2, 58, 31, 19, 61, 34, 3, 42, 11, 22, 46, 7, 61, 10, 42, 3,
01014     55, 32, 1, 58, 28, 44, 54, 4, 34, 23, 15, 56, 20, 37, 58, 6, 30, 38,
01015     18, 63, 9, 32, 5, 51, 3, 62, 37, 52, 18, 39, 23, 3, 51, 9, 47, 1, 23,
01016     43, 15, 60, 35, 11, 40, 1, 36, 31, 26, 57, 2, 37, 54, 18, 44, 58, 16},
01017    {5, 51, 3, 33, 43, 62, 21, 42, 35, 9, 48, 15, 36, 10, 22, 42, 20, 46,
01018     26, 56, 50, 12, 59, 3, 48, 19, 45, 53, 1, 27, 47, 17, 52, 24, 56, 11,
01019     51, 21, 37, 30, 20, 46, 14, 41, 1, 47, 33, 7, 41, 17, 35, 27, 20, 1,
01020     14, 54, 26, 33, 18, 47, 1, 44, 14, 59, 16, 52, 28, 18, 49, 31, 25, 34,
01021     63, 13, 51, 24, 9, 50, 3, 23, 38, 63, 7, 52, 29, 46, 11, 33, 50, 22,
01022     57, 36, 1, 57, 49, 17, 39, 28, 9, 35, 6, 27, 53, 15, 55, 30, 24, 58,
01023     36, 41, 11, 52, 32, 3, 44, 25, 62, 23, 51, 15, 42, 22, 50, 10, 39, 4,
01024     31, 35},
01025    {46, 22, 57, 17, 12, 39, 26, 5, 31, 59, 1, 45, 27, 62, 52, 7, 58, 33, 6,
01026     18, 39, 22, 33, 41, 57, 5, 35, 18, 40, 16, 60, 5, 29, 42, 7, 39, 27,
01027     44, 9, 47, 8, 26, 54, 22, 51, 29, 24, 49, 15, 61, 4, 51, 31, 63, 43, 6,
01028     50, 8, 39, 12, 53, 37, 23, 30, 40, 6, 62, 43, 14, 53, 2, 49, 7, 36, 17,
01029     41, 61, 37, 18, 56, 11, 18, 44, 35, 2, 19, 61, 0, 41, 14, 8, 30, 43,
01030     12, 24, 46, 14, 54, 42, 21, 44, 61, 10, 46, 37, 11, 44, 7, 18, 63, 20,
01031     29, 7, 49, 28, 54, 8, 43, 4, 48, 18, 63, 12, 29, 48, 24, 59, 20},
01032    {13, 36, 28, 54, 35, 2, 56, 46, 16, 49, 22, 40, 11, 34, 14, 43, 29, 12,
01033     63, 48, 2, 61, 7, 15, 28, 30, 50, 9, 61, 33, 38, 23, 54, 13, 61, 33, 3,
01034     59, 16, 35, 58, 40, 5, 38, 13, 57, 3, 58, 37, 21, 45, 12, 39, 7, 35,
01035     30, 13, 56, 22, 62, 27, 6, 55, 10, 48, 21, 33, 2, 38, 23, 40, 20, 44,
01036     29, 59, 4, 26, 12, 33, 47, 28, 53, 31, 13, 59, 41, 27, 49, 26, 54, 45,
01037     16, 53, 21, 35, 7, 59, 26, 11, 56, 1, 24, 33, 4, 28, 62, 21, 49, 31, 2,
01038     56, 39, 24, 58, 13, 17, 37, 21, 56, 10, 38, 0, 34, 55, 15, 43, 1, 52},
01039    {42, 9, 50, 6, 25, 60, 14, 38, 10, 29, 53, 18, 57, 3, 25, 51, 0, 53, 25,
01040     17, 29, 37, 52, 46, 0, 62, 14, 37, 4, 50, 10, 44, 0, 46, 20, 25, 50,
01041     19, 55, 0, 23, 31, 62, 34, 11, 45, 19, 32, 0, 53, 10, 59, 23, 47, 18,
01042     60, 42, 28, 37, 3, 50, 15, 35, 44, 0, 51, 27, 60, 9, 57, 16, 58, 11,
01043     22, 46, 15, 53, 48, 7, 42, 0, 60, 5, 49, 24, 54, 9, 17, 39, 5, 34, 62,
01044     3, 40, 60, 31, 0, 47, 29, 16, 49, 39, 59, 17, 50, 0, 40, 13, 53, 38,
01045     16, 46, 0, 42, 34, 60, 2, 53, 29, 31, 58, 46, 27, 6, 61, 8, 37, 28},
01046    {0, 63, 21, 40, 45, 18, 51, 23, 63, 34, 6, 43, 28, 38, 55, 19, 40, 35,
01047     8, 41, 54, 10, 21, 32, 39, 23, 53, 26, 55, 28, 22, 63, 30, 34, 9, 48,
01048     6, 38, 29, 43, 49, 6, 18, 52, 27, 61, 9, 43, 28, 42, 33, 26, 56, 3, 51,
01049     23, 0, 48, 16, 45, 32, 25, 63, 20, 57, 17, 42, 12, 35, 47, 5, 31, 39,
01050     56, 6, 30, 34, 21, 61, 25, 14, 40, 22, 38, 15, 6, 36, 56, 20, 60, 25,
01051     12, 51, 27, 10, 56, 42, 20, 36, 63, 32, 6, 21, 41, 12, 34, 60, 26, 5,
01052     48, 27, 10, 62, 19, 6, 47, 39, 14, 45, 7, 24, 17, 41, 32, 23, 51, 19,
01053     56},
01054    {45, 31, 15, 59, 4, 33, 7, 47, 0, 41, 13, 61, 4, 47, 9, 23, 60, 14, 57,
01055     31, 4, 45, 59, 6, 58, 10, 44, 20, 8, 42, 15, 6, 55, 17, 58, 31, 53, 12,
01056     61, 10, 15, 57, 43, 2, 23, 35, 48, 14, 54, 6, 18, 49, 15, 38, 11, 34,
01057     62, 9, 21, 58, 11, 41, 4, 31, 38, 8, 29, 55, 19, 36, 27, 52, 0, 25, 50,
01058     43, 1, 39, 8, 55, 35, 51, 10, 30, 45, 62, 29, 2, 46, 10, 32, 48, 18,
01059     38, 5, 22, 33, 8, 51, 3, 14, 44, 54, 25, 57, 30, 18, 52, 33, 22, 59,
01060     28, 36, 52, 32, 21, 26, 50, 5, 55, 35, 60, 14, 54, 4, 40, 16, 33},
01061    {27, 3, 49, 10, 30, 40, 55, 27, 57, 24, 52, 21, 32, 17, 60, 30, 5, 44,
01062     27, 49, 19, 34, 13, 24, 43, 36, 3, 49, 31, 59, 37, 48, 26, 41, 2, 41,
01063     14, 36, 21, 32, 40, 26, 13, 49, 55, 5, 16, 40, 25, 60, 36, 1, 63, 29,
01064     17, 44, 25, 40, 52, 5, 29, 47, 54, 13, 46, 24, 60, 4, 51, 22, 63, 14,
01065     45, 18, 12, 62, 17, 57, 19, 42, 3, 26, 58, 48, 1, 21, 40, 52, 23, 37,
01066     44, 1, 29, 58, 43, 50, 15, 61, 19, 45, 58, 28, 7, 48, 2, 46, 8, 42, 3,
01067     55, 8, 50, 12, 4, 55, 10, 63, 33, 20, 40, 11, 3, 46, 20, 48, 26, 61,
01068     11},
01069    {44, 56, 24, 36, 53, 19, 12, 37, 16, 44, 7, 36, 49, 54, 11, 37, 48, 21,
01070     15, 1, 62, 25, 47, 56, 16, 18, 51, 12, 40, 1, 24, 11, 52, 16, 23, 59,
01071     28, 1, 45, 53, 4, 60, 37, 21, 39, 30, 63, 20, 52, 10, 30, 45, 8, 41,
01072     54, 4, 57, 7, 34, 55, 36, 18, 23, 59, 2, 48, 11, 32, 44, 1, 41, 8, 33,
01073     54, 38, 23, 30, 46, 6, 29, 62, 18, 32, 16, 55, 34, 14, 11, 61, 7, 55,
01074     16, 53, 13, 23, 2, 55, 37, 26, 10, 33, 23, 36, 16, 38, 22, 56, 15, 24,
01075     43, 35, 17, 44, 40, 25, 46, 16, 1, 57, 25, 49, 36, 28, 62, 9, 35, 7,
01076     53},
01077    {17, 38, 8, 61, 1, 50, 26, 62, 3, 31, 56, 15, 1, 26, 40, 2, 34, 51, 56,
01078     36, 42, 9, 38, 2, 29, 60, 32, 57, 19, 62, 34, 47, 4, 57, 39, 7, 44, 63,
01079     24, 18, 46, 28, 8, 54, 1, 34, 7, 46, 3, 37, 50, 23, 57, 21, 13, 46, 31,
01080     20, 43, 15, 1, 61, 8, 33, 37, 17, 56, 26, 15, 49, 24, 59, 28, 3, 56, 9,
01081     52, 32, 13, 49, 10, 43, 5, 45, 8, 25, 59, 42, 28, 33, 19, 40, 8, 63,
01082     35, 47, 25, 4, 40, 52, 1, 60, 12, 53, 63, 9, 29, 60, 37, 19, 1, 62, 31,
01083     20, 58, 12, 41, 30, 43, 9, 18, 52, 22, 1, 39, 30, 58, 21},
01084    {13, 47, 29, 18, 43, 34, 5, 48, 20, 42, 10, 45, 30, 58, 20, 63, 24, 11,
01085     6, 28, 54, 14, 22, 52, 41, 7, 26, 5, 45, 15, 53, 13, 35, 27, 18, 50,
01086     12, 33, 5, 56, 10, 17, 45, 24, 59, 15, 50, 26, 56, 13, 19, 5, 32, 52,
01087     27, 36, 2, 61, 12, 26, 49, 40, 27, 52, 13, 50, 6, 39, 61, 34, 10, 37,
01088     48, 20, 41, 27, 2, 36, 59, 24, 54, 33, 63, 20, 38, 50, 3, 17, 52, 4,
01089     58, 27, 45, 21, 32, 11, 48, 17, 57, 20, 46, 38, 25, 43, 4, 34, 51, 6,
01090     13, 45, 57, 26, 6, 48, 2, 35, 53, 23, 61, 34, 59, 6, 42, 56, 13, 51, 2,
01091     41},
01092    {32, 5, 55, 23, 58, 14, 22, 52, 29, 15, 61, 25, 51, 8, 43, 13, 53, 41,
01093     46, 20, 3, 33, 63, 11, 48, 21, 54, 38, 28, 3, 30, 43, 21, 62, 9, 31,
01094     55, 22, 51, 29, 37, 62, 32, 12, 42, 29, 41, 9, 33, 44, 62, 28, 43, 1,
01095     59, 19, 48, 30, 51, 39, 24, 4, 58, 19, 42, 29, 22, 43, 3, 18, 53, 5,
01096     13, 50, 16, 60, 45, 21, 7, 40, 15, 0, 26, 53, 13, 31, 43, 24, 47, 31,
01097     15, 49, 2, 41, 6, 59, 29, 42, 9, 30, 14, 7, 49, 18, 31, 47, 20, 39, 49,
01098     32, 11, 41, 54, 15, 61, 18, 7, 38, 4, 13, 44, 28, 15, 32, 45, 19, 27,
01099     49},
01100    {63, 34, 11, 39, 2, 45, 37, 8, 59, 39, 33, 4, 36, 17, 48, 5, 29, 18, 32,
01101     61, 39, 50, 5, 27, 35, 0, 46, 12, 22, 49, 60, 6, 54, 0, 38, 49, 2, 42,
01102     15, 40, 0, 47, 20, 51, 3, 57, 18, 61, 22, 0, 39, 16, 55, 12, 35, 8, 41,
01103     22, 6, 59, 16, 45, 10, 36, 0, 62, 9, 54, 30, 58, 21, 43, 63, 31, 7, 35,
01104     12, 48, 58, 28, 47, 37, 41, 9, 57, 20, 61, 0, 36, 11, 57, 35, 23, 52,
01105     37, 18, 0, 62, 22, 55, 35, 62, 27, 54, 0, 15, 61, 28, 2, 59, 22, 9, 37,
01106     27, 33, 51, 29, 48, 19, 50, 25, 37, 10, 57, 5, 37, 60, 8},
01107    {20, 25, 46, 52, 31, 60, 12, 55, 0, 19, 11, 46, 62, 35, 23, 38, 57, 0,
01108     55, 10, 16, 30, 58, 44, 17, 59, 29, 63, 42, 8, 36, 20, 33, 46, 16, 61,
01109     25, 35, 8, 54, 26, 7, 58, 22, 34, 6, 47, 14, 53, 31, 48, 9, 37, 25, 49,
01110     63, 16, 55, 45, 14, 34, 63, 21, 53, 25, 33, 46, 16, 35, 7, 46, 29, 0,
01111     39, 25, 55, 22, 34, 18, 4, 56, 11, 23, 51, 28, 6, 39, 14, 62, 44, 19,
01112     8, 60, 12, 56, 28, 50, 34, 39, 5, 51, 3, 41, 12, 57, 35, 10, 53, 25,
01113     17, 52, 30, 47, 0, 43, 14, 5, 57, 31, 55, 0, 63, 47, 23, 54, 24, 14,
01114     43},
01115    {0, 57, 16, 6, 26, 19, 35, 28, 49, 42, 54, 26, 21, 1, 59, 27, 9, 47, 26,
01116     44, 50, 22, 13, 40, 8, 37, 10, 34, 17, 56, 25, 58, 13, 27, 44, 9, 20,
01117     58, 31, 17, 60, 36, 10, 41, 53, 25, 36, 39, 4, 24, 58, 17, 60, 4, 22,
01118     38, 10, 32, 0, 50, 31, 7, 28, 47, 12, 57, 5, 26, 52, 23, 14, 40, 57,
01119     17, 47, 5, 53, 1, 44, 31, 19, 60, 46, 2, 35, 48, 30, 54, 22, 5, 51, 39,
01120     25, 31, 4, 43, 14, 9, 45, 16, 24, 44, 19, 29, 40, 23, 44, 7, 38, 42, 4,
01121     63, 12, 54, 23, 59, 22, 42, 8, 15, 40, 21, 8, 34, 3, 41, 30, 50},
01122    {39, 10, 48, 33, 41, 54, 5, 47, 23, 13, 32, 7, 52, 44, 14, 39, 58, 18,
01123     35, 6, 37, 2, 60, 24, 55, 19, 53, 2, 51, 32, 1, 41, 51, 4, 40, 29, 47,
01124     3, 52, 44, 13, 49, 28, 16, 1, 62, 11, 27, 52, 35, 5, 42, 29, 47, 14,
01125     56, 28, 53, 26, 38, 9, 56, 40, 3, 38, 15, 41, 60, 1, 37, 50, 25, 11,
01126     28, 61, 19, 42, 62, 10, 52, 39, 6, 32, 14, 58, 17, 7, 26, 42, 34, 27,
01127     10, 54, 40, 20, 63, 26, 53, 21, 61, 32, 7, 59, 48, 3, 56, 18, 31, 58,
01128     14, 49, 21, 36, 16, 45, 9, 36, 24, 62, 45, 27, 31, 53, 17, 49, 12, 62,
01129     18},
01130    {28, 59, 21, 58, 2, 16, 38, 9, 62, 3, 56, 41, 10, 31, 50, 4, 32, 52, 12,
01131     63, 23, 46, 33, 31, 4, 48, 25, 43, 14, 23, 47, 11, 22, 55, 14, 60, 23,
01132     37, 11, 39, 23, 2, 45, 56, 31, 43, 19, 55, 16, 46, 21, 51, 11, 33, 44,
01133     2, 41, 18, 5, 52, 23, 44, 17, 60, 27, 49, 11, 32, 44, 10, 54, 2, 56,
01134     33, 8, 38, 13, 29, 36, 16, 24, 63, 27, 51, 21, 43, 56, 12, 49, 3, 59,
01135     48, 1, 15, 46, 7, 36, 2, 47, 11, 50, 27, 37, 13, 33, 8, 51, 46, 1, 34,
01136     28, 40, 3, 33, 60, 29, 47, 1, 35, 11, 59, 42, 2, 60, 26, 46, 6, 35},
01137    {4, 43, 9, 29, 36, 63, 24, 44, 20, 50, 30, 17, 60, 22, 16, 43, 25, 3,
01138     42, 19, 51, 15, 8, 54, 42, 15, 61, 5, 39, 57, 18, 61, 31, 48, 34, 2,
01139     50, 19, 57, 5, 63, 33, 19, 38, 13, 27, 48, 7, 32, 61, 2, 26, 58, 6, 24,
01140     50, 13, 61, 42, 20, 62, 2, 35, 20, 51, 4, 62, 18, 23, 58, 20, 31, 43,
01141     15, 51, 45, 26, 50, 4, 55, 45, 3, 35, 9, 38, 1, 32, 61, 20, 45, 17, 33,
01142     24, 57, 29, 51, 22, 58, 38, 30, 15, 1, 54, 21, 63, 43, 26, 12, 24, 56,
01143     8, 60, 50, 19, 5, 52, 13, 54, 17, 50, 4, 16, 36, 12, 32, 56, 22, 54},
01144    {51, 25, 40, 53, 12, 49, 15, 57, 34, 7, 38, 47, 2, 36, 55, 8, 61, 30,
01145     56, 7, 28, 59, 48, 11, 27, 35, 21, 45, 28, 36, 9, 38, 6, 16, 24, 63,
01146     10, 32, 28, 43, 21, 53, 5, 60, 8, 57, 3, 45, 11, 37, 15, 54, 40, 20,
01147     62, 36, 27, 34, 11, 48, 30, 15, 54, 8, 30, 42, 22, 34, 48, 13, 35, 63,
01148     4, 37, 22, 2, 59, 9, 41, 23, 13, 41, 49, 18, 59, 24, 40, 5, 37, 30, 9,
01149     61, 44, 6, 37, 11, 33, 17, 5, 55, 41, 60, 23, 39, 17, 5, 30, 62, 41,
01150     16, 46, 25, 11, 56, 39, 26, 20, 38, 29, 39, 22, 52, 44, 20, 48, 1, 38,
01151     14},
01152    {15, 33, 2, 18, 44, 6, 27, 0, 32, 61, 25, 12, 58, 28, 40, 20, 47, 13,
01153     34, 43, 38, 1, 23, 62, 40, 0, 51, 10, 63, 3, 52, 26, 44, 30, 45, 6, 41,
01154     54, 0, 51, 12, 30, 46, 24, 49, 22, 40, 33, 63, 23, 43, 30, 9, 47, 0,
01155     17, 54, 7, 57, 3, 37, 47, 24, 46, 13, 55, 7, 52, 2, 42, 6, 26, 49, 18,
01156     60, 34, 16, 57, 33, 20, 61, 30, 8, 54, 14, 46, 12, 53, 16, 55, 38, 13,
01157     22, 53, 18, 59, 46, 27, 43, 19, 32, 10, 45, 6, 49, 36, 52, 2, 20, 55,
01158     6, 39, 32, 15, 44, 3, 58, 10, 63, 6, 56, 30, 7, 58, 9, 40, 19, 63},
01159    {10, 47, 61, 23, 55, 31, 52, 42, 17, 45, 4, 51, 27, 6, 15, 53, 0, 49,
01160     26, 10, 56, 18, 36, 6, 20, 58, 32, 30, 13, 49, 19, 56, 0, 59, 12, 53,
01161     27, 17, 38, 25, 48, 9, 15, 36, 14, 30, 59, 17, 0, 50, 8, 58, 18, 56,
01162     31, 45, 21, 41, 29, 19, 60, 6, 32, 59, 0, 36, 29, 39, 19, 59, 46, 12,
01163     55, 30, 10, 47, 24, 3, 28, 48, 0, 55, 44, 27, 33, 4, 63, 29, 49, 0, 26,
01164     50, 34, 2, 42, 14, 0, 62, 9, 56, 3, 52, 28, 34, 58, 9, 20, 48, 37, 32,
01165     22, 53, 0, 62, 27, 49, 34, 46, 21, 33, 41, 14, 25, 37, 53, 29, 31, 45},
01166    {56, 28, 7, 37, 11, 36, 20, 9, 54, 14, 39, 19, 34, 63, 45, 37, 24, 17,
01167     60, 31, 21, 45, 53, 29, 47, 15, 7, 55, 40, 23, 34, 14, 42, 20, 37, 35,
01168     15, 59, 7, 62, 34, 40, 59, 1, 51, 42, 10, 28, 54, 21, 35, 5, 38, 13,
01169     36, 4, 59, 12, 39, 53, 15, 43, 9, 21, 39, 62, 16, 56, 25, 9, 32, 38, 0,
01170     41, 14, 51, 40, 53, 43, 11, 37, 17, 5, 22, 57, 39, 19, 7, 42, 21, 60,
01171     10, 31, 63, 25, 52, 30, 49, 36, 25, 48, 17, 61, 14, 22, 42, 29, 13, 60,
01172     11, 47, 18, 35, 41, 7, 23, 4, 16, 51, 11, 0, 48, 61, 3, 17, 50, 5, 24},
01173    {0, 42, 21, 49, 60, 3, 57, 40, 29, 48, 23, 56, 42, 11, 22, 5, 59, 39, 4,
01174     50, 3, 41, 12, 57, 25, 50, 44, 18, 4, 46, 7, 62, 33, 50, 4, 56, 21, 32,
01175     43, 18, 3, 23, 55, 34, 20, 4, 53, 38, 12, 46, 29, 52, 25, 61, 23, 51,
01176     26, 46, 1, 34, 25, 57, 28, 51, 26, 11, 50, 3, 44, 28, 53, 21, 57, 27,
01177     62, 6, 31, 19, 8, 63, 26, 59, 36, 47, 15, 29, 50, 25, 35, 47, 18, 41,
01178     4, 48, 8, 40, 12, 23, 6, 44, 13, 40, 1, 31, 55, 0, 61, 43, 4, 50, 26,
01179     58, 9, 53, 24, 61, 42, 55, 31, 43, 57, 20, 34, 27, 43, 8, 59, 39},
01180    {18, 51, 30, 13, 26, 16, 46, 22, 2, 59, 8, 30, 1, 48, 33, 51, 29, 9, 46,
01181     16, 62, 14, 33, 2, 38, 9, 27, 60, 37, 26, 53, 17, 28, 10, 24, 46, 2,
01182     49, 8, 57, 29, 45, 6, 26, 62, 44, 18, 25, 61, 3, 42, 14, 49, 10, 43, 6,
01183     17, 32, 63, 10, 49, 4, 40, 14, 45, 33, 22, 37, 12, 61, 5, 17, 43, 7,
01184     23, 37, 15, 58, 49, 13, 39, 21, 10, 52, 1, 62, 9, 56, 12, 2, 58, 28,
01185     36, 16, 56, 28, 56, 35, 20, 63, 24, 37, 51, 8, 45, 25, 16, 33, 27, 38,
01186     2, 44, 13, 30, 17, 36, 12, 26, 5, 18, 28, 47, 13, 60, 23, 45, 13, 33},
01187    {55, 4, 62, 34, 52, 38, 7, 63, 32, 37, 13, 53, 25, 62, 18, 12, 55, 41,
01188     27, 35, 24, 49, 31, 52, 17, 63, 34, 1, 56, 12, 41, 2, 48, 58, 39, 16,
01189     61, 27, 41, 52, 13, 19, 50, 39, 11, 31, 57, 6, 32, 40, 20, 55, 1, 28,
01190     33, 57, 48, 8, 37, 22, 44, 18, 53, 1, 61, 5, 54, 16, 47, 36, 50, 24,
01191     55, 34, 48, 45, 1, 30, 33, 46, 2, 50, 32, 42, 25, 34, 43, 21, 38, 52,
01192     23, 45, 14, 54, 21, 4, 44, 16, 53, 29, 10, 47, 19, 57, 12, 54, 39, 10,
01193     51, 15, 63, 21, 57, 40, 51, 1, 48, 57, 37, 62, 2, 38, 9, 52, 1, 35, 58,
01194     22},
01195    {36, 46, 10, 42, 1, 27, 43, 15, 50, 21, 45, 16, 41, 3, 35, 44, 20, 1,
01196     57, 11, 55, 7, 43, 8, 22, 42, 13, 46, 21, 39, 31, 60, 22, 5, 29, 44,
01197     11, 35, 20, 4, 36, 58, 32, 15, 47, 2, 36, 48, 16, 60, 8, 35, 44, 63,
01198     16, 2, 40, 26, 55, 14, 58, 35, 24, 31, 19, 42, 31, 58, 1, 29, 10, 40,
01199     2, 19, 12, 54, 22, 61, 7, 24, 56, 5, 28, 16, 54, 3, 15, 58, 6, 30, 8,
01200     62, 1, 43, 31, 47, 7, 59, 1, 38, 58, 4, 34, 27, 38, 5, 31, 59, 7, 46,
01201     30, 3, 34, 6, 28, 59, 20, 8, 32, 15, 53, 24, 55, 31, 19, 49, 11, 26},
01202    {2, 24, 16, 58, 19, 55, 5, 35, 10, 61, 4, 28, 57, 24, 58, 7, 31, 47, 22,
01203     38, 19, 28, 61, 36, 54, 5, 59, 29, 6, 52, 15, 11, 43, 36, 8, 54, 52, 1,
01204     62, 25, 47, 9, 1, 60, 28, 53, 24, 14, 46, 27, 51, 22, 12, 24, 38, 53,
01205     20, 11, 51, 3, 29, 7, 48, 63, 8, 49, 9, 21, 52, 14, 63, 32, 46, 60, 35,
01206     4, 41, 16, 52, 35, 18, 42, 59, 7, 36, 61, 45, 27, 33, 51, 19, 39, 34,
01207     11, 61, 18, 33, 41, 28, 15, 54, 22, 42, 3, 49, 21, 47, 18, 36, 23, 55,
01208     19, 48, 24, 45, 10, 33, 44, 50, 40, 7, 35, 15, 41, 63, 6, 40, 54},
01209    {62, 41, 32, 8, 47, 28, 60, 24, 44, 30, 38, 49, 9, 33, 14, 40, 50, 14,
01210     60, 2, 54, 40, 0, 20, 25, 39, 16, 49, 24, 35, 57, 47, 19, 61, 33, 18,
01211     23, 37, 13, 55, 31, 43, 22, 41, 17, 8, 42, 58, 0, 37, 5, 56, 31, 54, 7,
01212     30, 60, 33, 42, 17, 59, 39, 12, 27, 38, 17, 35, 41, 27, 45, 20, 7, 25,
01213     15, 29, 58, 27, 47, 11, 40, 14, 54, 23, 46, 19, 31, 11, 40, 13, 49, 5,
01214     58, 24, 51, 26, 6, 50, 20, 49, 9, 32, 46, 17, 60, 14, 63, 24, 1, 57,
01215     41, 9, 43, 14, 62, 16, 52, 3, 27, 14, 22, 61, 45, 4, 28, 9, 47, 29,
01216     17},
01217    {5, 50, 12, 53, 38, 18, 11, 51, 0, 55, 17, 6, 47, 54, 19, 63, 5, 26, 34,
01218     45, 13, 30, 47, 58, 10, 48, 32, 3, 62, 9, 26, 0, 25, 14, 50, 3, 47, 30,
01219     42, 16, 6, 63, 12, 49, 33, 55, 21, 10, 34, 63, 18, 41, 3, 47, 19, 43,
01220     0, 49, 8, 28, 46, 20, 52, 0, 56, 24, 60, 3, 59, 5, 39, 57, 48, 52, 9,
01221     38, 3, 21, 26, 60, 0, 32, 12, 38, 4, 48, 53, 0, 60, 15, 29, 44, 18, 10,
01222     38, 57, 13, 60, 2, 26, 62, 7, 50, 29, 35, 8, 40, 53, 28, 12, 60, 33,
01223     38, 5, 37, 29, 60, 39, 56, 0, 30, 18, 50, 34, 59, 25, 14, 44},
01224    {20, 31, 60, 22, 3, 49, 33, 25, 40, 13, 34, 59, 22, 36, 0, 28, 37, 56,
01225     8, 18, 51, 16, 4, 45, 27, 12, 53, 42, 18, 44, 51, 31, 55, 40, 28, 58,
01226     7, 60, 10, 51, 27, 37, 24, 56, 5, 26, 44, 29, 50, 23, 45, 11, 34, 15,
01227     59, 27, 13, 23, 62, 37, 4, 57, 15, 32, 42, 6, 47, 11, 30, 43, 23, 13,
01228     0, 36, 18, 44, 63, 51, 37, 29, 49, 20, 57, 27, 62, 9, 24, 35, 23, 53,
01229     37, 3, 42, 55, 0, 36, 23, 39, 31, 43, 17, 37, 24, 11, 52, 43, 19, 32,
01230     5, 50, 26, 0, 56, 21, 54, 11, 19, 6, 47, 25, 59, 42, 12, 54, 21, 3, 38,
01231     57},
01232    {48, 0, 35, 27, 44, 14, 59, 7, 57, 46, 26, 2, 42, 12, 52, 43, 10, 27,
01233     53, 42, 32, 62, 37, 21, 34, 61, 7, 23, 36, 4, 38, 12, 41, 5, 17, 45,
01234     22, 27, 39, 21, 59, 0, 45, 18, 39, 62, 3, 38, 14, 7, 54, 26, 61, 39, 9,
01235     52, 45, 36, 18, 50, 10, 34, 44, 22, 50, 14, 36, 55, 17, 34, 53, 62, 33,
01236     26, 56, 6, 31, 12, 6, 53, 9, 44, 2, 50, 20, 40, 55, 17, 47, 7, 26, 63,
01237     22, 32, 48, 16, 46, 8, 52, 12, 57, 41, 0, 56, 25, 3, 61, 14, 45, 35,
01238     18, 44, 12, 46, 23, 42, 32, 51, 35, 10, 17, 36, 23, 1, 45, 52, 32, 10},
01239    {37, 15, 43, 8, 63, 39, 21, 31, 16, 37, 19, 62, 30, 46, 17, 60, 21, 48,
01240     1, 23, 6, 25, 11, 56, 1, 40, 30, 58, 15, 54, 21, 59, 9, 63, 35, 56, 11,
01241     51, 2, 46, 34, 14, 53, 7, 30, 11, 51, 19, 60, 40, 30, 1, 24, 50, 20,
01242     32, 3, 56, 5, 25, 31, 13, 61, 2, 29, 60, 25, 20, 51, 2, 27, 8, 18, 42,
01243     10, 45, 21, 34, 43, 17, 62, 29, 41, 14, 34, 6, 30, 43, 2, 57, 33, 13,
01244     45, 12, 27, 62, 4, 55, 21, 35, 5, 27, 45, 33, 16, 47, 30, 54, 22, 10,
01245     51, 27, 63, 7, 49, 1, 58, 22, 15, 43, 53, 7, 57, 39, 27, 12, 61, 24},
01246    {56, 51, 26, 56, 19, 2, 41, 54, 5, 52, 9, 48, 6, 23, 39, 4, 32, 15, 63,
01247     35, 59, 49, 43, 15, 52, 19, 50, 9, 46, 33, 1, 29, 48, 20, 32, 1, 38,
01248     33, 19, 54, 9, 32, 24, 48, 58, 35, 16, 48, 4, 52, 13, 57, 33, 5, 45,
01249     59, 15, 29, 41, 55, 47, 39, 23, 53, 9, 40, 4, 57, 10, 44, 48, 40, 50,
01250     14, 61, 24, 55, 1, 59, 22, 33, 8, 51, 25, 58, 46, 11, 59, 20, 41, 17,
01251     51, 6, 56, 35, 25, 42, 30, 15, 58, 48, 18, 61, 9, 58, 39, 13, 2, 37,
01252     59, 40, 2, 31, 16, 34, 41, 8, 30, 62, 3, 29, 48, 33, 5, 63, 16, 41, 7},
01253    {22, 4, 46, 11, 33, 51, 29, 10, 62, 24, 43, 27, 15, 58, 50, 25, 54, 44,
01254     9, 38, 18, 3, 29, 57, 32, 5, 26, 43, 17, 61, 24, 52, 8, 42, 23, 53, 15,
01255     61, 7, 28, 57, 43, 4, 40, 20, 2, 43, 25, 32, 35, 21, 43, 17, 48, 10,
01256     22, 38, 54, 11, 21, 1, 58, 16, 30, 48, 18, 46, 32, 38, 13, 22, 4, 59,
01257     35, 2, 51, 30, 39, 15, 47, 4, 56, 13, 37, 1, 28, 16, 52, 32, 9, 61, 29,
01258     38, 19, 3, 52, 10, 48, 1, 32, 11, 40, 20, 36, 6, 22, 49, 29, 55, 6, 20,
01259     56, 36, 52, 19, 60, 26, 46, 18, 54, 40, 13, 20, 46, 35, 19, 49, 29},
01260    {61, 17, 34, 53, 23, 6, 48, 35, 20, 40, 1, 56, 36, 29, 11, 34, 7, 41,
01261     14, 30, 55, 20, 46, 8, 24, 38, 63, 2, 37, 10, 45, 14, 34, 49, 6, 13,
01262     44, 25, 49, 41, 21, 12, 61, 15, 54, 29, 63, 12, 56, 8, 49, 2, 62, 36,
01263     28, 61, 0, 25, 41, 63, 35, 8, 44, 6, 37, 62, 7, 21, 63, 28, 55, 31, 16,
01264     24, 41, 19, 9, 57, 27, 36, 18, 42, 31, 62, 22, 55, 38, 4, 27, 47, 1,
01265     40, 14, 54, 43, 20, 60, 23, 38, 63, 25, 51, 2, 53, 26, 63, 10, 42, 17,
01266     34, 47, 25, 13, 5, 44, 11, 55, 2, 38, 27, 6, 60, 52, 25, 9, 55, 1, 40},
01267    {8, 30, 58, 3, 42, 61, 17, 38, 13, 59, 32, 10, 54, 3, 51, 20, 61, 26,
01268     57, 2, 46, 33, 12, 60, 41, 13, 48, 29, 55, 20, 39, 27, 57, 18, 62, 29,
01269     55, 2, 31, 16, 37, 50, 26, 36, 6, 46, 9, 41, 27, 57, 23, 39, 26, 6, 51,
01270     12, 31, 46, 7, 16, 27, 52, 19, 56, 26, 12, 33, 53, 1, 41, 8, 57, 46, 7,
01271     54, 32, 47, 5, 49, 11, 60, 23, 5, 48, 10, 43, 19, 63, 35, 24, 49, 21,
01272     59, 5, 31, 37, 14, 44, 7, 42, 6, 30, 46, 13, 44, 32, 19, 50, 4, 58, 8,
01273     30, 62, 38, 28, 53, 21, 36, 13, 50, 21, 33, 15, 2, 44, 31, 14, 47},
01274    {37, 13, 39, 16, 28, 9, 57, 0, 25, 49, 21, 45, 18, 47, 12, 42, 0, 49,
01275     22, 39, 16, 53, 25, 36, 0, 52, 22, 16, 6, 60, 4, 51, 0, 26, 37, 47, 10,
01276     36, 63, 5, 57, 0, 18, 59, 23, 33, 51, 19, 0, 44, 15, 11, 54, 17, 42,
01277     35, 53, 18, 58, 33, 49, 4, 34, 42, 0, 50, 43, 25, 16, 49, 34, 20, 37,
01278     28, 12, 63, 16, 38, 25, 44, 0, 40, 52, 17, 35, 3, 50, 14, 8, 53, 11,
01279     36, 25, 45, 9, 62, 0, 54, 28, 17, 50, 55, 15, 24, 57, 0, 53, 34, 23,
01280     41, 15, 45, 0, 49, 16, 4, 48, 9, 63, 45, 0, 42, 58, 37, 61, 22, 54,
01281     26},
01282    {0, 50, 21, 47, 54, 36, 27, 45, 52, 4, 34, 15, 63, 29, 37, 59, 17, 31,
01283     6, 61, 28, 5, 48, 18, 59, 27, 34, 56, 44, 31, 35, 12, 41, 59, 16, 3,
01284     40, 20, 50, 22, 30, 40, 52, 10, 45, 3, 59, 22, 37, 61, 29, 46, 31, 58,
01285     2, 22, 9, 43, 3, 39, 14, 61, 24, 54, 15, 29, 11, 60, 39, 17, 5, 61, 0,
01286     44, 50, 3, 31, 14, 58, 21, 54, 28, 15, 45, 60, 26, 33, 58, 44, 22, 60,
01287     2, 57, 34, 49, 27, 18, 34, 21, 59, 29, 4, 36, 41, 8, 39, 28, 11, 62,
01288     26, 53, 20, 35, 24, 59, 32, 29, 39, 24, 31, 57, 23, 11, 28, 5, 36, 11,
01289     59},
01290    {44, 32, 63, 5, 20, 12, 41, 7, 30, 61, 42, 8, 39, 5, 33, 8, 24, 53, 45,
01291     11, 37, 58, 7, 44, 10, 50, 3, 40, 8, 22, 53, 19, 46, 9, 33, 52, 24, 58,
01292     8, 44, 13, 47, 8, 34, 38, 30, 14, 47, 7, 34, 4, 55, 9, 19, 40, 49, 56,
01293     26, 60, 21, 30, 45, 10, 19, 40, 58, 23, 36, 3, 52, 45, 23, 54, 13, 22,
01294     42, 53, 45, 7, 33, 10, 36, 57, 6, 29, 12, 41, 0, 30, 15, 41, 30, 17, 7,
01295     16, 53, 40, 56, 2, 39, 12, 61, 10, 52, 31, 60, 16, 45, 1, 37, 7, 61,
01296     40, 10, 43, 17, 58, 7, 54, 14, 4, 51, 39, 49, 18, 56, 42, 20},
01297    {14, 6, 24, 36, 56, 49, 22, 60, 18, 14, 23, 51, 26, 57, 21, 52, 41, 14,
01298     35, 50, 19, 31, 40, 23, 33, 14, 63, 17, 32, 47, 7, 62, 23, 30, 56, 11,
01299     42, 27, 14, 60, 35, 19, 28, 61, 17, 55, 25, 39, 53, 17, 42, 21, 38, 63,
01300     25, 5, 14, 36, 12, 50, 1, 37, 59, 32, 2, 51, 6, 56, 27, 32, 11, 30, 38,
01301     26, 60, 8, 26, 19, 62, 39, 50, 2, 21, 39, 53, 23, 56, 19, 49, 39, 5,
01302     46, 55, 23, 42, 4, 31, 11, 47, 26, 45, 22, 48, 18, 21, 5, 48, 25, 57,
01303     14, 47, 30, 3, 56, 12, 50, 1, 42, 19, 47, 35, 17, 8, 30, 45, 25, 4,
01304     51},
01305    {28, 58, 43, 1, 31, 8, 33, 2, 44, 55, 32, 1, 60, 12, 46, 27, 4, 62, 23,
01306     1, 56, 13, 62, 2, 54, 36, 25, 51, 1, 57, 26, 42, 3, 49, 17, 38, 1, 48,
01307     31, 4, 54, 3, 50, 24, 1, 49, 5, 63, 13, 27, 52, 1, 48, 13, 45, 33, 52,
01308     30, 46, 20, 55, 28, 6, 48, 24, 38, 20, 47, 14, 62, 48, 9, 58, 4, 36,
01309     30, 56, 1, 34, 12, 18, 63, 25, 48, 4, 16, 37, 7, 62, 10, 52, 28, 13,
01310     50, 36, 63, 24, 51, 15, 58, 8, 33, 1, 38, 56, 35, 42, 9, 33, 51, 22,
01311     18, 48, 32, 27, 37, 23, 61, 33, 11, 59, 29, 62, 1, 53, 10, 60, 33},
01312    {12, 39, 17, 52, 26, 46, 53, 38, 25, 11, 48, 36, 16, 43, 2, 35, 55, 17,
01313     39, 29, 43, 9, 28, 45, 20, 5, 46, 12, 42, 28, 13, 52, 36, 6, 60, 22,
01314     54, 17, 62, 39, 25, 42, 15, 55, 44, 20, 31, 10, 35, 57, 24, 32, 29, 6,
01315     59, 18, 7, 62, 3, 41, 10, 44, 16, 54, 13, 62, 31, 9, 41, 1, 21, 43, 18,
01316     47, 15, 40, 11, 49, 28, 55, 46, 30, 8, 43, 32, 61, 28, 47, 25, 34, 21,
01317     61, 32, 1, 20, 9, 46, 6, 35, 19, 41, 54, 27, 63, 14, 3, 51, 20, 62, 2,
01318     38, 55, 8, 21, 63, 6, 46, 9, 26, 51, 3, 24, 43, 34, 16, 41, 18, 48},
01319    {62, 23, 55, 9, 15, 62, 19, 13, 58, 40, 6, 30, 54, 19, 50, 31, 10, 44,
01320     6, 59, 21, 47, 51, 15, 60, 39, 30, 54, 21, 61, 19, 33, 14, 29, 43, 11,
01321     34, 45, 7, 21, 10, 56, 36, 6, 38, 11, 58, 42, 2, 47, 11, 60, 50, 16,
01322     41, 28, 38, 23, 47, 17, 35, 63, 22, 33, 42, 5, 45, 17, 53, 35, 25, 56,
01323     33, 6, 51, 19, 60, 23, 43, 15, 5, 40, 58, 13, 51, 1, 45, 11, 54, 3, 43,
01324     8, 37, 48, 59, 29, 39, 21, 61, 43, 3, 31, 10, 44, 24, 29, 60, 12, 28,
01325     40, 11, 25, 43, 52, 14, 41, 16, 57, 44, 20, 40, 55, 12, 21, 57, 27, 35,
01326     2},
01327    {37, 6, 31, 42, 40, 4, 29, 50, 0, 20, 63, 28, 9, 58, 14, 24, 63, 26, 48,
01328     16, 34, 4, 32, 38, 23, 11, 58, 4, 37, 9, 45, 5, 63, 48, 26, 57, 2, 28,
01329     32, 51, 46, 29, 13, 62, 27, 46, 28, 18, 50, 15, 40, 4, 19, 34, 54, 0,
01330     53, 9, 26, 58, 28, 5, 49, 0, 57, 27, 19, 60, 29, 8, 59, 12, 37, 63, 24,
01331     46, 3, 37, 6, 52, 26, 32, 20, 36, 9, 22, 59, 18, 35, 51, 14, 57, 17,
01332     24, 12, 44, 56, 0, 30, 13, 59, 20, 49, 17, 54, 43, 6, 34, 46, 17, 58,
01333     36, 0, 34, 29, 54, 25, 2, 36, 15, 60, 6, 37, 46, 4, 50, 9, 45},
01334    {19, 59, 48, 3, 24, 60, 44, 22, 34, 51, 15, 45, 41, 5, 33, 47, 0, 37,
01335     12, 55, 25, 54, 8, 57, 0, 47, 18, 34, 49, 15, 55, 24, 40, 20, 8, 35,
01336     53, 13, 41, 18, 0, 59, 22, 33, 4, 52, 8, 60, 24, 36, 31, 56, 45, 26,
01337     10, 43, 15, 56, 36, 4, 51, 14, 39, 30, 12, 55, 36, 2, 39, 49, 4, 44,
01338     17, 0, 32, 13, 53, 35, 59, 17, 62, 0, 55, 24, 52, 38, 31, 6, 42, 19,
01339     29, 40, 4, 54, 33, 5, 16, 27, 52, 37, 23, 55, 7, 37, 0, 39, 23, 49, 4,
01340     53, 31, 15, 59, 10, 50, 4, 60, 34, 48, 7, 31, 49, 27, 14, 62, 22, 53,
01341     29},
01342    {46, 21, 14, 51, 36, 17, 7, 57, 10, 32, 3, 37, 22, 60, 39, 18, 56, 20,
01343     42, 3, 36, 10, 44, 26, 41, 29, 53, 27, 2, 39, 30, 52, 0, 59, 15, 48,
01344     23, 61, 6, 58, 37, 12, 40, 49, 16, 39, 20, 44, 0, 62, 8, 21, 3, 59, 23,
01345     32, 49, 31, 12, 44, 22, 59, 18, 50, 24, 7, 43, 52, 15, 23, 41, 26, 51,
01346     28, 55, 39, 21, 27, 10, 42, 12, 45, 27, 47, 3, 15, 63, 26, 55, 0, 60,
01347     26, 45, 18, 62, 38, 58, 49, 8, 47, 4, 33, 46, 29, 57, 13, 56, 16, 59,
01348     21, 5, 47, 23, 39, 18, 44, 13, 22, 28, 53, 19, 0, 58, 32, 41, 7, 26,
01349     13},
01350    {0, 56, 34, 28, 11, 55, 31, 47, 26, 41, 56, 13, 53, 28, 11, 49, 7, 52,
01351     32, 61, 50, 22, 63, 17, 13, 56, 7, 19, 43, 62, 10, 21, 37, 32, 43, 4,
01352     38, 19, 44, 25, 31, 54, 5, 23, 61, 30, 53, 12, 35, 22, 43, 53, 37, 48,
01353     7, 62, 20, 2, 61, 41, 8, 34, 47, 9, 63, 34, 28, 10, 55, 33, 14, 57, 7,
01354     47, 9, 61, 4, 49, 31, 50, 21, 38, 8, 16, 57, 44, 33, 5, 49, 36, 12, 50,
01355     7, 34, 10, 25, 2, 22, 36, 15, 26, 61, 18, 9, 22, 46, 32, 8, 27, 37, 44,
01356     30, 55, 3, 62, 24, 38, 56, 5, 45, 38, 24, 43, 10, 19, 54, 39, 61},
01357    {41, 30, 8, 63, 43, 23, 38, 3, 62, 19, 8, 49, 25, 1, 58, 30, 23, 40, 9,
01358     28, 18, 40, 6, 38, 49, 22, 35, 59, 8, 27, 50, 5, 56, 17, 11, 50, 30, 9,
01359     55, 2, 51, 19, 34, 47, 9, 41, 6, 26, 48, 57, 14, 28, 17, 12, 39, 13,
01360     37, 46, 25, 19, 54, 27, 1, 37, 16, 45, 20, 60, 1, 48, 20, 38, 31, 22,
01361     42, 15, 19, 44, 1, 61, 6, 34, 56, 40, 29, 10, 20, 46, 13, 22, 41, 23,
01362     59, 42, 30, 51, 45, 13, 63, 53, 42, 12, 51, 38, 62, 2, 26, 41, 50, 1,
01363     61, 10, 19, 42, 31, 8, 49, 32, 12, 63, 9, 52, 16, 56, 36, 2, 31, 16},
01364    {52, 5, 47, 20, 1, 53, 12, 50, 16, 35, 43, 21, 33, 43, 16, 44, 3, 59,
01365     14, 46, 1, 30, 60, 33, 2, 45, 12, 42, 31, 47, 14, 33, 46, 25, 55, 27,
01366     60, 36, 16, 42, 14, 46, 26, 1, 55, 15, 63, 32, 2, 38, 5, 47, 33, 61,
01367     30, 52, 4, 57, 6, 38, 11, 43, 61, 24, 52, 3, 31, 22, 42, 10, 62, 3, 59,
01368     11, 35, 57, 33, 54, 24, 14, 29, 48, 18, 2, 60, 41, 53, 24, 32, 62, 3,
01369     53, 15, 1, 55, 17, 32, 40, 6, 31, 1, 40, 28, 5, 35, 52, 19, 63, 13, 33,
01370     17, 41, 52, 26, 15, 57, 1, 20, 42, 17, 35, 27, 48, 5, 25, 50, 44, 11},
01371    {35, 25, 38, 57, 33, 17, 40, 6, 59, 27, 54, 5, 61, 10, 52, 26, 36, 19,
01372     51, 35, 57, 48, 11, 20, 54, 25, 61, 16, 1, 58, 24, 61, 3, 39, 7, 47, 1,
01373     22, 49, 28, 63, 10, 58, 32, 17, 36, 45, 19, 51, 29, 59, 10, 50, 1, 23,
01374     42, 18, 29, 51, 21, 56, 32, 14, 5, 40, 58, 47, 13, 54, 35, 29, 45, 18,
01375     52, 26, 2, 38, 8, 46, 36, 58, 11, 52, 35, 17, 28, 1, 58, 9, 39, 17, 28,
01376     37, 48, 20, 9, 57, 24, 50, 19, 58, 16, 48, 25, 43, 11, 35, 6, 45, 24,
01377     56, 4, 36, 7, 47, 35, 52, 28, 59, 30, 2, 61, 21, 33, 63, 12, 18, 59},
01378    {3, 49, 15, 10, 27, 61, 25, 45, 30, 0, 14, 47, 31, 38, 17, 62, 7, 55,
01379     27, 4, 15, 24, 42, 52, 10, 34, 5, 51, 36, 18, 41, 11, 35, 21, 62, 13,
01380     33, 57, 8, 35, 5, 40, 21, 43, 52, 3, 24, 56, 11, 16, 33, 25, 41, 20,
01381     55, 8, 60, 35, 15, 48, 2, 57, 30, 49, 18, 25, 6, 39, 17, 57, 7, 25, 43,
01382     5, 49, 16, 62, 22, 55, 4, 25, 43, 23, 7, 50, 11, 37, 48, 14, 51, 33,
01383     57, 7, 27, 39, 46, 4, 29, 11, 43, 34, 56, 7, 60, 20, 54, 30, 57, 22,
01384     49, 9, 33, 54, 14, 63, 23, 6, 43, 10, 40, 50, 13, 44, 8, 38, 33, 46,
01385     23},
01386    {55, 39, 22, 50, 44, 4, 36, 9, 52, 23, 37, 59, 21, 2, 46, 13, 31, 41,
01387     11, 45, 62, 29, 6, 37, 19, 48, 30, 23, 44, 7, 53, 28, 54, 16, 41, 29,
01388     44, 18, 52, 24, 60, 15, 48, 7, 27, 59, 9, 34, 42, 54, 7, 63, 4, 46, 31,
01389     27, 45, 0, 40, 26, 34, 17, 37, 10, 53, 29, 36, 50, 2, 27, 51, 11, 61,
01390     37, 23, 41, 30, 7, 18, 50, 39, 14, 63, 32, 45, 61, 19, 30, 25, 44, 2,
01391     47, 23, 63, 11, 34, 59, 37, 60, 3, 22, 14, 44, 30, 15, 0, 47, 15, 3,
01392     38, 61, 20, 27, 45, 11, 39, 51, 16, 55, 3, 22, 54, 29, 58, 1, 57, 6,
01393     29},
01394    {9, 17, 60, 2, 34, 56, 20, 62, 39, 12, 49, 6, 29, 56, 34, 48, 0, 58, 22,
01395     38, 18, 43, 56, 0, 63, 14, 55, 3, 59, 31, 15, 45, 0, 49, 6, 58, 3, 38,
01396     12, 45, 0, 37, 29, 57, 13, 39, 30, 49, 0, 23, 44, 36, 16, 57, 13, 54,
01397     11, 24, 63, 9, 53, 7, 62, 42, 0, 59, 15, 23, 63, 34, 40, 16, 32, 0, 53,
01398     12, 48, 28, 59, 33, 0, 53, 9, 27, 3, 22, 54, 5, 56, 9, 61, 13, 42, 14,
01399     52, 19, 0, 21, 47, 27, 53, 36, 3, 50, 39, 58, 25, 40, 53, 28, 12, 50,
01400     0, 59, 32, 2, 21, 34, 26, 46, 37, 7, 18, 47, 24, 14, 53, 42},
01401    {61, 32, 13, 54, 29, 7, 46, 13, 28, 57, 18, 41, 53, 15, 9, 39, 24, 49,
01402     33, 3, 53, 9, 26, 32, 40, 28, 46, 39, 25, 9, 56, 21, 63, 37, 26, 22,
01403     51, 27, 17, 56, 31, 53, 4, 43, 22, 46, 12, 18, 60, 40, 20, 26, 50, 21,
01404     39, 5, 49, 33, 16, 44, 22, 46, 20, 32, 24, 45, 8, 43, 12, 46, 4, 48,
01405     56, 20, 29, 58, 3, 40, 10, 42, 31, 21, 47, 41, 56, 38, 15, 42, 36, 27,
01406     20, 33, 55, 3, 26, 44, 31, 54, 12, 35, 9, 63, 28, 10, 21, 32, 9, 60,
01407     17, 8, 43, 29, 40, 16, 36, 48, 60, 7, 57, 14, 62, 31, 42, 15, 36, 40,
01408     20, 26},
01409    {0, 37, 47, 23, 41, 18, 32, 48, 1, 35, 8, 25, 4, 26, 63, 20, 54, 8, 16,
01410     61, 35, 23, 51, 15, 58, 7, 12, 20, 50, 34, 42, 4, 38, 10, 32, 47, 8,
01411     60, 41, 20, 9, 25, 50, 19, 62, 1, 37, 56, 28, 8, 53, 11, 3, 58, 34, 43,
01412     19, 60, 38, 4, 58, 31, 3, 51, 11, 55, 38, 30, 21, 58, 19, 26, 9, 44,
01413     36, 13, 46, 20, 62, 24, 13, 60, 5, 28, 12, 34, 7, 59, 0, 53, 45, 6, 38,
01414     30, 50, 7, 62, 16, 41, 5, 46, 18, 55, 42, 51, 5, 45, 23, 34, 48, 19,
01415     58, 5, 25, 54, 19, 13, 41, 28, 21, 0, 49, 10, 60, 4, 51, 9, 45},
01416    {19, 28, 6, 58, 10, 51, 4, 22, 55, 42, 60, 45, 34, 51, 42, 5, 30, 45,
01417     27, 40, 13, 47, 4, 49, 21, 38, 60, 29, 2, 57, 17, 27, 52, 19, 61, 14,
01418     30, 34, 2, 44, 63, 33, 11, 35, 16, 51, 25, 6, 14, 47, 31, 61, 37, 29,
01419     18, 8, 52, 2, 28, 54, 13, 41, 15, 62, 35, 18, 2, 60, 6, 33, 41, 61, 31,
01420     6, 56, 17, 34, 50, 6, 52, 44, 35, 16, 51, 59, 24, 48, 18, 31, 40, 16,
01421     49, 21, 60, 17, 39, 10, 49, 32, 57, 24, 39, 1, 25, 18, 62, 37, 12, 56,
01422     1, 37, 11, 52, 44, 9, 30, 47, 4, 51, 40, 55, 25, 34, 27, 56, 30, 32,
01423     54},
01424    {63, 40, 49, 15, 43, 26, 63, 38, 16, 20, 30, 12, 57, 14, 19, 60, 36, 12,
01425     59, 2, 57, 17, 42, 31, 1, 44, 16, 35, 47, 11, 32, 48, 13, 43, 1, 39,
01426     51, 12, 57, 23, 6, 40, 53, 3, 55, 31, 39, 60, 35, 44, 5, 15, 45, 1, 62,
01427     41, 26, 14, 47, 22, 36, 27, 50, 9, 26, 47, 52, 28, 54, 16, 1, 13, 51,
01428     39, 23, 63, 1, 30, 15, 26, 2, 57, 19, 37, 1, 44, 21, 50, 13, 63, 8, 24,
01429     56, 1, 35, 25, 58, 20, 2, 28, 14, 51, 33, 59, 13, 30, 4, 49, 31, 24,
01430     63, 26, 33, 3, 58, 38, 62, 24, 32, 8, 17, 45, 5, 48, 18, 3, 43, 11},
01431    {21, 4, 24, 34, 59, 1, 37, 11, 53, 5, 47, 2, 22, 40, 32, 1, 24, 50, 21,
01432     29, 38, 25, 63, 8, 55, 24, 53, 6, 62, 23, 59, 3, 54, 20, 58, 24, 5, 46,
01433     15, 38, 48, 14, 27, 42, 23, 7, 46, 10, 17, 58, 25, 52, 23, 32, 49, 12,
01434     55, 30, 40, 7, 59, 1, 56, 21, 39, 4, 23, 15, 37, 46, 55, 42, 21, 4, 48,
01435     8, 45, 54, 37, 55, 32, 8, 46, 10, 30, 54, 4, 41, 25, 29, 36, 48, 11,
01436     43, 14, 47, 5, 43, 53, 36, 61, 10, 45, 6, 41, 54, 27, 43, 16, 55, 6,
01437     46, 18, 42, 23, 15, 1, 45, 12, 60, 37, 22, 62, 12, 39, 59, 16, 52},
01438    {47, 35, 56, 7, 19, 46, 31, 50, 33, 24, 61, 35, 50, 7, 53, 44, 55, 6,
01439     46, 10, 52, 5, 21, 43, 36, 10, 18, 41, 26, 37, 8, 29, 40, 36, 9, 49,
01440     34, 26, 61, 21, 7, 59, 18, 62, 29, 54, 20, 32, 51, 0, 40, 10, 55, 6,
01441     20, 36, 9, 61, 5, 51, 44, 19, 33, 43, 13, 57, 40, 63, 8, 24, 29, 10,
01442     60, 34, 27, 40, 25, 18, 10, 42, 21, 49, 26, 62, 38, 12, 33, 61, 5, 57,
01443     2, 19, 54, 28, 62, 22, 38, 31, 16, 7, 22, 47, 29, 17, 35, 8, 20, 51, 2,
01444     40, 22, 50, 13, 61, 28, 53, 35, 20, 56, 30, 2, 53, 14, 41, 23, 34, 8,
01445     31},
01446    {12, 2, 42, 29, 52, 13, 21, 8, 55, 14, 41, 17, 28, 58, 23, 11, 17, 36,
01447     31, 62, 17, 34, 50, 14, 28, 61, 33, 52, 2, 51, 17, 45, 7, 25, 62, 30,
01448     18, 55, 0, 42, 30, 35, 45, 1, 12, 48, 3, 63, 21, 36, 30, 48, 19, 59,
01449     43, 27, 46, 17, 34, 25, 12, 29, 53, 6, 48, 31, 11, 34, 49, 3, 36, 50,
01450     19, 47, 14, 61, 11, 36, 58, 4, 60, 14, 39, 22, 6, 52, 15, 35, 17, 46,
01451     31, 42, 9, 34, 3, 52, 12, 60, 26, 56, 40, 2, 53, 23, 57, 38, 62, 14,
01452     36, 59, 10, 31, 39, 6, 49, 9, 41, 26, 5, 48, 43, 27, 33, 58, 1, 50, 25,
01453     57},
01454    {61, 37, 15, 61, 3, 39, 58, 43, 26, 0, 44, 10, 47, 3, 37, 63, 28, 43,
01455     13, 39, 3, 57, 30, 59, 0, 48, 5, 43, 13, 22, 60, 33, 55, 15, 42, 4, 52,
01456     10, 45, 13, 54, 4, 24, 49, 37, 26, 41, 14, 42, 9, 61, 13, 38, 23, 3,
01457     53, 0, 58, 21, 42, 63, 10, 17, 61, 25, 0, 58, 28, 17, 44, 57, 12, 27,
01458     0, 55, 5, 52, 28, 23, 47, 29, 0, 43, 17, 58, 28, 47, 23, 55, 10, 58,
01459     23, 51, 40, 18, 33, 45, 0, 49, 8, 32, 61, 19, 48, 0, 26, 7, 47, 29, 18,
01460     44, 0, 56, 34, 20, 59, 15, 51, 37, 18, 10, 52, 7, 20, 46, 9, 38, 17},
01461    {6, 27, 48, 23, 45, 29, 5, 18, 38, 62, 27, 56, 20, 32, 15, 9, 48, 0, 54,
01462     22, 45, 20, 7, 41, 23, 39, 19, 27, 58, 31, 44, 0, 12, 50, 23, 56, 20,
01463     39, 32, 59, 16, 52, 33, 9, 57, 22, 6, 58, 28, 50, 24, 2, 56, 35, 16,
01464     45, 32, 38, 15, 54, 2, 38, 46, 22, 35, 45, 20, 5, 52, 25, 7, 35, 59,
01465     32, 22, 43, 38, 3, 51, 16, 34, 53, 32, 50, 3, 40, 8, 43, 0, 39, 27, 4,
01466     14, 61, 8, 55, 15, 41, 20, 44, 27, 13, 39, 11, 46, 42, 54, 33, 4, 52,
01467     23, 61, 14, 25, 43, 2, 33, 11, 63, 29, 61, 17, 40, 55, 22, 62, 28, 44},
01468    {20, 54, 8, 56, 35, 10, 63, 31, 52, 12, 48, 6, 59, 41, 52, 33, 19, 58,
01469     25, 49, 11, 37, 47, 12, 54, 15, 56, 35, 7, 47, 16, 53, 28, 34, 5, 37,
01470     28, 8, 48, 3, 28, 38, 18, 61, 16, 43, 53, 32, 4, 17, 47, 27, 44, 8, 63,
01471     10, 25, 49, 6, 37, 24, 52, 32, 3, 50, 12, 41, 56, 38, 14, 62, 20, 40,
01472     16, 53, 31, 18, 63, 41, 9, 59, 7, 13, 25, 57, 20, 63, 26, 53, 18, 48,
01473     62, 30, 46, 21, 25, 58, 29, 36, 4, 55, 34, 6, 60, 31, 16, 21, 12, 58,
01474     38, 9, 29, 47, 7, 52, 30, 57, 44, 22, 0, 35, 45, 3, 31, 14, 36, 0, 51},
01475    {42, 14, 33, 24, 16, 49, 40, 2, 22, 33, 16, 36, 25, 1, 21, 61, 38, 8,
01476     33, 4, 62, 26, 29, 60, 6, 46, 30, 11, 63, 4, 36, 40, 19, 57, 46, 11,
01477     41, 63, 22, 25, 58, 10, 46, 2, 34, 27, 11, 38, 56, 34, 12, 53, 18, 33,
01478     41, 51, 13, 28, 60, 20, 47, 14, 29, 59, 16, 62, 8, 22, 32, 47, 9, 49,
01479     2, 44, 7, 12, 45, 6, 20, 27, 45, 24, 62, 42, 36, 11, 33, 15, 37, 7, 32,
01480     10, 37, 1, 35, 50, 6, 11, 63, 24, 52, 15, 50, 24, 3, 37, 56, 27, 34,
01481     22, 49, 16, 36, 62, 17, 39, 4, 15, 54, 24, 50, 8, 58, 26, 49, 54, 11,
01482     30},
01483    {4, 59, 41, 1, 53, 12, 25, 45, 59, 7, 51, 39, 54, 14, 46, 4, 27, 53, 16,
01484     44, 18, 51, 1, 32, 25, 2, 50, 40, 20, 54, 24, 9, 62, 2, 27, 60, 1, 17,
01485     36, 50, 6, 40, 30, 55, 41, 19, 49, 1, 21, 60, 40, 5, 62, 1, 22, 30, 57,
01486     4, 43, 31, 1, 55, 40, 7, 27, 37, 30, 54, 1, 19, 42, 30, 56, 26, 62, 49,
01487     24, 57, 37, 56, 2, 39, 16, 5, 30, 55, 3, 49, 60, 23, 56, 44, 17, 52,
01488     13, 42, 28, 48, 18, 45, 9, 37, 21, 41, 58, 10, 48, 1, 63, 5, 41, 57, 2,
01489     24, 12, 48, 27, 42, 32, 46, 13, 38, 19, 34, 5, 41, 25, 60},
01490    {39, 28, 21, 46, 32, 57, 36, 9, 19, 42, 4, 29, 11, 43, 30, 49, 13, 42,
01491     35, 56, 9, 39, 15, 52, 36, 61, 18, 26, 45, 14, 31, 48, 21, 43, 14, 33,
01492     49, 54, 14, 44, 21, 62, 13, 23, 8, 62, 15, 51, 44, 7, 30, 37, 20, 42,
01493     56, 7, 39, 18, 50, 11, 61, 9, 19, 43, 57, 2, 48, 11, 39, 60, 28, 4, 37,
01494     17, 35, 1, 33, 11, 31, 14, 48, 19, 35, 51, 46, 21, 44, 29, 12, 41, 2,
01495     22, 58, 26, 54, 4, 59, 38, 2, 33, 57, 1, 63, 13, 28, 51, 15, 40, 18,
01496     45, 8, 30, 43, 37, 54, 19, 8, 59, 21, 6, 60, 29, 55, 10, 63, 15, 47,
01497     17},
01498    {3, 50, 10, 62, 18, 5, 27, 49, 60, 23, 55, 18, 62, 24, 56, 10, 59, 28,
01499     2, 23, 34, 59, 43, 20, 10, 42, 8, 49, 1, 37, 57, 6, 51, 29, 53, 7, 23,
01500     31, 5, 32, 51, 0, 35, 54, 45, 31, 5, 26, 36, 24, 55, 15, 48, 29, 14,
01501     48, 26, 60, 21, 41, 36, 26, 50, 33, 14, 44, 17, 24, 52, 15, 46, 23, 54,
01502     6, 47, 21, 60, 50, 4, 53, 29, 61, 8, 23, 1, 60, 19, 6, 53, 16, 47, 34,
01503     6, 39, 16, 31, 12, 20, 53, 22, 30, 43, 25, 46, 35, 6, 44, 32, 53, 26,
01504     55, 19, 11, 59, 5, 33, 51, 1, 35, 53, 25, 3, 42, 23, 44, 32, 7, 53},
01505    {22, 44, 37, 6, 26, 51, 38, 0, 34, 13, 31, 46, 3, 37, 6, 19, 40, 21, 47,
01506     63, 12, 5, 29, 55, 22, 58, 34, 28, 60, 22, 11, 41, 17, 38, 9, 44, 59,
01507     39, 56, 19, 11, 47, 25, 15, 3, 39, 57, 17, 61, 11, 46, 3, 58, 9, 54,
01508     35, 2, 34, 8, 45, 15, 56, 5, 23, 53, 33, 63, 35, 4, 59, 10, 51, 13, 61,
01509     29, 41, 15, 25, 43, 19, 40, 10, 54, 33, 41, 12, 38, 51, 31, 26, 61, 9,
01510     30, 45, 24, 62, 49, 40, 10, 61, 14, 49, 5, 17, 54, 20, 60, 23, 3, 13,
01511     35, 50, 32, 23, 46, 27, 38, 63, 16, 12, 39, 48, 18, 51, 1, 27, 56, 35},
01512    {63, 15, 30, 55, 43, 14, 57, 17, 53, 44, 7, 48, 26, 50, 32, 60, 0, 53,
01513     14, 31, 50, 24, 46, 0, 38, 13, 4, 52, 16, 45, 30, 59, 0, 25, 55, 35,
01514     16, 10, 26, 42, 58, 29, 60, 38, 50, 22, 28, 47, 0, 50, 28, 19, 33, 39,
01515     11, 44, 16, 52, 24, 59, 3, 38, 27, 51, 0, 21, 7, 42, 26, 34, 21, 40,
01516     33, 18, 39, 3, 54, 38, 8, 59, 0, 44, 27, 15, 58, 28, 57, 9, 43, 0, 36,
01517     50, 20, 59, 8, 34, 0, 27, 47, 7, 36, 19, 56, 32, 0, 38, 11, 29, 62, 47,
01518     6, 61, 0, 41, 14, 56, 10, 23, 45, 31, 57, 8, 36, 13, 58, 38, 11, 19},
01519    {0, 34, 12, 47, 21, 2, 40, 30, 11, 25, 61, 20, 40, 15, 35, 22, 45, 36,
01520     7, 41, 17, 57, 9, 48, 32, 62, 44, 24, 35, 3, 54, 13, 33, 63, 19, 4, 48,
01521     22, 62, 2, 37, 8, 33, 6, 20, 52, 9, 32, 43, 13, 39, 63, 25, 4, 49, 23,
01522     62, 32, 9, 30, 48, 18, 63, 12, 46, 29, 58, 13, 48, 8, 57, 31, 0, 51, 9,
01523     58, 12, 22, 47, 29, 35, 22, 49, 5, 46, 4, 34, 20, 63, 24, 56, 11, 41,
01524     3, 51, 19, 56, 35, 17, 58, 28, 42, 9, 45, 59, 26, 51, 42, 17, 36, 25,
01525     15, 53, 21, 44, 3, 30, 55, 5, 50, 21, 28, 61, 32, 6, 49, 28, 46},
01526    {58, 42, 60, 4, 31, 59, 22, 63, 35, 38, 9, 54, 1, 57, 8, 51, 16, 58, 27,
01527     53, 3, 38, 30, 15, 27, 6, 19, 56, 10, 50, 21, 36, 47, 5, 43, 28, 51,
01528     32, 13, 46, 18, 54, 16, 43, 63, 12, 36, 59, 22, 34, 5, 52, 17, 59, 27,
01529     41, 0, 19, 55, 37, 13, 43, 6, 34, 41, 10, 36, 55, 19, 44, 3, 16, 58,
01530     27, 49, 25, 32, 62, 17, 55, 13, 63, 18, 52, 25, 37, 17, 48, 13, 32, 5,
01531     46, 28, 37, 14, 43, 25, 5, 51, 39, 3, 52, 33, 22, 8, 40, 12, 4, 57, 9,
01532     46, 39, 28, 58, 13, 62, 17, 42, 19, 36, 0, 47, 16, 43, 24, 21, 54, 13},
01533    {25, 9, 23, 50, 36, 8, 45, 14, 3, 51, 16, 28, 44, 12, 42, 29, 4, 26, 10,
01534     47, 22, 61, 18, 54, 51, 39, 46, 13, 41, 26, 58, 7, 18, 39, 12, 57, 15,
01535     1, 52, 27, 41, 23, 48, 1, 27, 45, 18, 2, 57, 26, 55, 8, 43, 31, 6, 58,
01536     14, 51, 40, 5, 61, 31, 24, 54, 17, 60, 22, 1, 39, 30, 53, 45, 36, 13,
01537     43, 5, 45, 2, 37, 6, 34, 42, 2, 39, 10, 62, 7, 54, 40, 18, 60, 15, 52,
01538     21, 63, 8, 55, 46, 15, 30, 23, 13, 62, 16, 50, 24, 58, 31, 48, 21, 34,
01539     2, 49, 7, 31, 37, 26, 48, 9, 61, 40, 11, 52, 2, 60, 40, 4, 37},
01540    {52, 28, 39, 16, 54, 19, 29, 55, 42, 20, 58, 33, 24, 63, 18, 55, 39, 62,
01541     43, 34, 12, 40, 6, 35, 2, 25, 8, 62, 34, 1, 31, 42, 61, 27, 53, 24, 40,
01542     61, 34, 8, 59, 4, 30, 56, 40, 6, 53, 42, 10, 48, 16, 37, 12, 46, 21,
01543     36, 47, 11, 28, 45, 22, 10, 57, 2, 49, 31, 14, 44, 61, 11, 25, 6, 23,
01544     63, 18, 36, 28, 56, 20, 51, 11, 48, 27, 56, 32, 22, 45, 30, 2, 42, 27,
01545     39, 1, 44, 23, 31, 38, 22, 11, 61, 43, 54, 4, 47, 35, 2, 44, 16, 28,
01546     54, 12, 62, 18, 43, 10, 52, 1, 58, 33, 15, 29, 56, 20, 34, 9, 30, 48,
01547     17},
01548    {46, 2, 56, 11, 41, 1, 49, 6, 27, 47, 2, 48, 5, 32, 37, 3, 13, 19, 32,
01549     1, 55, 28, 60, 17, 43, 59, 32, 20, 49, 16, 55, 23, 14, 46, 2, 36, 6,
01550     30, 20, 49, 12, 47, 35, 14, 21, 60, 29, 14, 35, 24, 46, 1, 56, 29, 53,
01551     8, 33, 23, 56, 1, 35, 46, 20, 39, 26, 4, 53, 28, 17, 38, 60, 34, 48, 9,
01552     55, 15, 46, 7, 41, 31, 60, 24, 16, 36, 1, 59, 19, 52, 35, 6, 55, 11,
01553     59, 33, 7, 57, 4, 29, 48, 1, 19, 26, 37, 30, 18, 63, 37, 6, 59, 1, 40,
01554     24, 56, 33, 46, 22, 35, 7, 24, 53, 39, 5, 26, 45, 55, 18, 62, 7},
01555    {20, 60, 29, 34, 20, 62, 33, 52, 10, 36, 13, 60, 41, 21, 50, 27, 56, 49,
01556     8, 51, 21, 45, 11, 48, 8, 23, 53, 3, 29, 44, 5, 52, 9, 32, 50, 17, 43,
01557     56, 3, 38, 24, 10, 62, 25, 51, 9, 33, 49, 61, 7, 30, 62, 22, 19, 2, 42,
01558     63, 5, 49, 18, 60, 15, 52, 7, 43, 56, 23, 50, 5, 50, 2, 20, 41, 30, 1,
01559     52, 22, 61, 14, 26, 3, 43, 53, 7, 47, 28, 11, 14, 23, 58, 33, 25, 47,
01560     13, 50, 17, 40, 54, 34, 60, 41, 6, 59, 14, 50, 7, 25, 55, 20, 42, 51,
01561     8, 27, 4, 16, 60, 28, 50, 44, 3, 22, 49, 63, 12, 33, 1, 43, 31},
01562    {36, 5, 46, 8, 44, 24, 13, 39, 25, 57, 31, 18, 8, 52, 10, 45, 6, 30, 36,
01563     24, 63, 4, 33, 26, 57, 40, 15, 56, 37, 12, 40, 25, 37, 58, 11, 63, 21,
01564     45, 16, 60, 31, 53, 18, 33, 3, 45, 23, 0, 20, 54, 40, 15, 50, 38, 60,
01565     16, 25, 42, 29, 38, 7, 41, 25, 62, 18, 33, 8, 35, 42, 16, 32, 56, 12,
01566     39, 59, 19, 34, 9, 49, 38, 57, 12, 21, 50, 14, 40, 61, 44, 50, 9, 49,
01567     19, 3, 29, 35, 62, 12, 24, 7, 18, 52, 32, 10, 46, 21, 41, 32, 11, 36,
01568     29, 14, 34, 60, 38, 54, 11, 41, 14, 19, 57, 32, 16, 7, 41, 51, 25, 14,
01569     57},
01570    {53, 18, 26, 50, 15, 58, 4, 63, 17, 43, 7, 40, 61, 35, 15, 41, 23, 60,
01571     16, 38, 14, 42, 19, 50, 0, 31, 10, 46, 27, 63, 18, 60, 0, 20, 29, 39,
01572     8, 26, 37, 5, 42, 0, 44, 39, 57, 17, 58, 41, 28, 37, 4, 32, 9, 44, 12,
01573     31, 54, 10, 59, 14, 27, 53, 12, 36, 0, 47, 13, 63, 21, 58, 10, 24, 50,
01574     27, 4, 26, 44, 53, 31, 0, 18, 42, 29, 33, 57, 4, 32, 26, 0, 38, 16, 61,
01575     41, 53, 20, 0, 42, 44, 49, 27, 10, 56, 39, 0, 57, 15, 53, 49, 3, 61,
01576     22, 47, 17, 5, 49, 26, 2, 63, 39, 10, 47, 27, 37, 23, 4, 59, 38, 10},
01577    {23, 39, 61, 3, 37, 28, 48, 31, 0, 34, 51, 23, 2, 26, 58, 0, 53, 11, 46,
01578     1, 57, 29, 52, 14, 37, 61, 21, 35, 2, 49, 7, 34, 47, 55, 4, 33, 54, 13,
01579     58, 52, 19, 50, 22, 7, 13, 29, 36, 11, 51, 17, 60, 25, 55, 4, 34, 51,
01580     0, 35, 20, 48, 32, 3, 51, 30, 59, 28, 40, 3, 46, 29, 54, 43, 7, 62, 47,
01581     11, 39, 4, 23, 46, 55, 8, 63, 5, 25, 37, 18, 46, 21, 56, 31, 5, 36, 8,
01582     45, 58, 26, 15, 2, 36, 47, 21, 29, 44, 25, 34, 3, 27, 43, 10, 52, 0,
01583     45, 30, 24, 36, 43, 18, 34, 59, 0, 52, 61, 15, 44, 19, 30, 49},
01584    {0, 27, 12, 43, 54, 9, 22, 53, 21, 46, 15, 55, 29, 47, 20, 33, 39, 28,
01585     59, 35, 9, 44, 5, 24, 47, 7, 52, 17, 56, 22, 30, 42, 14, 26, 45, 18,
01586     49, 1, 24, 34, 11, 27, 55, 32, 61, 47, 2, 56, 6, 44, 13, 47, 36, 27,
01587     58, 22, 16, 47, 40, 4, 57, 38, 21, 45, 16, 9, 56, 26, 11, 38, 0, 22,
01588     36, 17, 33, 57, 16, 30, 62, 15, 35, 40, 20, 45, 59, 10, 54, 8, 63, 13,
01589     52, 27, 22, 57, 28, 12, 32, 51, 55, 22, 63, 4, 16, 54, 12, 62, 45, 19,
01590     58, 13, 32, 40, 20, 56, 7, 57, 9, 54, 6, 29, 42, 21, 8, 55, 35, 47, 6,
01591     41},
01592    {56, 33, 58, 32, 19, 35, 42, 6, 59, 11, 38, 5, 49, 12, 62, 7, 52, 17, 5,
01593     25, 54, 20, 61, 31, 54, 27, 41, 11, 44, 5, 59, 12, 36, 51, 10, 61, 28,
01594     41, 48, 9, 43, 63, 5, 40, 20, 8, 49, 26, 34, 21, 58, 1, 18, 45, 7, 39,
01595     61, 26, 8, 50, 23, 10, 63, 5, 55, 37, 19, 49, 52, 15, 59, 47, 13, 54,
01596     1, 25, 42, 58, 10, 48, 3, 27, 50, 1, 17, 48, 34, 41, 16, 40, 2, 45, 10,
01597     39, 17, 61, 5, 38, 19, 9, 41, 31, 60, 38, 5, 23, 36, 8, 30, 55, 24, 63,
01598     12, 48, 14, 51, 31, 20, 45, 25, 12, 50, 32, 2, 28, 11, 62, 14},
01599    {44, 16, 7, 48, 1, 62, 16, 50, 27, 33, 61, 25, 17, 44, 31, 14, 22, 43,
01600     32, 48, 18, 40, 8, 36, 3, 16, 33, 62, 23, 38, 25, 53, 2, 21, 41, 6, 22,
01601     15, 59, 29, 16, 37, 26, 15, 52, 42, 23, 15, 54, 39, 10, 30, 53, 11, 49,
01602     24, 2, 43, 55, 17, 34, 44, 15, 31, 24, 44, 2, 32, 7, 35, 25, 5, 40, 45,
01603     29, 51, 6, 21, 37, 52, 24, 60, 13, 31, 53, 23, 2, 28, 49, 24, 31, 60,
01604     20, 51, 1, 34, 48, 14, 59, 33, 50, 1, 18, 33, 48, 60, 17, 51, 39, 6,
01605     38, 2, 35, 29, 40, 23, 1, 62, 15, 53, 37, 17, 46, 57, 40, 51, 24, 22},
01606    {5, 37, 52, 24, 45, 13, 40, 3, 45, 9, 19, 42, 56, 4, 37, 46, 56, 2, 63,
01607     11, 51, 1, 49, 13, 59, 45, 39, 1, 48, 15, 58, 9, 46, 31, 54, 35, 57,
01608     38, 3, 46, 56, 4, 47, 57, 1, 30, 38, 63, 3, 46, 28, 63, 41, 14, 33, 62,
01609     19, 32, 13, 28, 61, 1, 53, 42, 11, 60, 22, 62, 27, 42, 61, 31, 19, 8,
01610     61, 12, 32, 55, 2, 18, 33, 12, 43, 36, 9, 62, 30, 55, 6, 58, 35, 7, 43,
01611     29, 54, 23, 43, 30, 3, 25, 11, 45, 52, 28, 7, 14, 42, 1, 22, 50, 16,
01612     53, 19, 59, 4, 46, 33, 41, 4, 35, 58, 5, 26, 13, 20, 2, 34, 54},
01613    {30, 63, 21, 10, 26, 55, 29, 59, 23, 39, 53, 1, 36, 24, 59, 27, 10, 34,
01614     23, 38, 30, 60, 22, 42, 28, 19, 9, 57, 30, 19, 43, 33, 13, 63, 3, 19,
01615     11, 50, 31, 20, 14, 34, 10, 35, 17, 59, 7, 31, 19, 25, 50, 5, 20, 57,
01616     29, 6, 52, 41, 4, 46, 20, 37, 26, 17, 49, 6, 39, 18, 53, 14, 3, 49, 57,
01617     23, 34, 48, 14, 41, 28, 38, 56, 6, 58, 25, 39, 19, 43, 15, 37, 11, 47,
01618     18, 53, 4, 37, 9, 62, 21, 53, 40, 57, 24, 13, 40, 56, 26, 47, 31, 59,
01619     25, 45, 27, 10, 43, 21, 61, 13, 27, 48, 9, 23, 43, 31, 62, 38, 59, 9,
01620     47},
01621    {25, 4, 40, 60, 34, 6, 18, 36, 8, 57, 12, 30, 49, 14, 6, 54, 41, 16, 50,
01622     6, 43, 15, 34, 4, 53, 24, 50, 35, 4, 51, 7, 55, 28, 24, 39, 44, 60, 7,
01623     25, 62, 42, 53, 24, 61, 28, 45, 52, 12, 48, 37, 9, 35, 43, 3, 37, 48,
01624     12, 58, 30, 52, 9, 59, 6, 57, 33, 29, 48, 4, 37, 45, 20, 34, 10, 39, 0,
01625     60, 22, 45, 8, 63, 21, 42, 14, 49, 3, 56, 11, 46, 21, 61, 0, 42, 25,
01626     13, 63, 17, 36, 8, 46, 16, 6, 35, 63, 0, 21, 37, 4, 57, 9, 34, 5, 61,
01627     48, 32, 8, 37, 54, 17, 56, 30, 60, 0, 50, 16, 7, 29, 42, 17},
01628    {32, 50, 15, 48, 2, 43, 52, 25, 47, 16, 32, 63, 21, 52, 40, 19, 0, 61,
01629     29, 58, 20, 56, 26, 46, 12, 55, 6, 22, 62, 32, 17, 40, 0, 49, 34, 8,
01630     27, 32, 48, 0, 21, 39, 5, 44, 12, 6, 22, 40, 0, 57, 16, 60, 23, 17, 54,
01631     22, 36, 15, 24, 39, 19, 34, 47, 23, 0, 54, 13, 51, 24, 9, 55, 16, 52,
01632     27, 44, 20, 4, 54, 26, 49, 0, 30, 46, 16, 29, 51, 34, 4, 52, 28, 33,
01633     15, 57, 39, 26, 49, 0, 56, 27, 31, 48, 20, 43, 29, 53, 11, 46, 19, 41,
01634     13, 55, 18, 0, 57, 26, 51, 2, 44, 6, 38, 14, 40, 22, 45, 36, 53, 3,
01635     57},
01636    {44, 12, 37, 28, 22, 57, 11, 38, 0, 51, 9, 41, 4, 29, 11, 47, 33, 45,
01637     12, 26, 3, 36, 9, 63, 31, 16, 38, 44, 14, 47, 25, 61, 20, 58, 15, 47,
01638     17, 57, 13, 36, 9, 51, 18, 29, 50, 36, 54, 20, 61, 27, 32, 13, 53, 44,
01639     9, 27, 0, 63, 45, 2, 56, 10, 14, 43, 41, 28, 58, 11, 35, 60, 30, 41, 6,
01640     63, 11, 51, 37, 32, 15, 10, 35, 53, 5, 61, 22, 7, 26, 59, 23, 9, 44,
01641     48, 21, 3, 51, 32, 24, 41, 12, 61, 2, 55, 9, 15, 35, 58, 28, 15, 62,
01642     30, 37, 23, 42, 29, 11, 17, 35, 24, 63, 20, 52, 28, 8, 55, 11, 23, 47,
01643     19},
01644    {0, 56, 8, 53, 14, 31, 61, 20, 55, 28, 62, 18, 35, 60, 25, 57, 7, 23,
01645     39, 54, 47, 17, 43, 0, 40, 59, 29, 2, 56, 10, 37, 5, 43, 11, 29, 52, 1,
01646     23, 54, 41, 59, 30, 55, 1, 62, 15, 33, 4, 43, 10, 47, 39, 1, 31, 40,
01647     60, 49, 33, 7, 55, 26, 50, 31, 61, 8, 18, 21, 32, 44, 1, 25, 47, 18,
01648     36, 30, 23, 59, 7, 40, 59, 27, 19, 38, 32, 44, 54, 40, 17, 38, 60, 27,
01649     6, 35, 55, 10, 14, 44, 5, 50, 17, 38, 26, 42, 50, 18, 3, 44, 52, 2, 49,
01650     7, 52, 15, 46, 62, 39, 55, 10, 31, 48, 3, 58, 33, 18, 61, 34, 13, 59},
01651    {39, 27, 63, 20, 35, 41, 4, 45, 26, 5, 38, 13, 44, 2, 50, 17, 37, 52, 2,
01652     13, 28, 58, 24, 51, 21, 8, 34, 48, 27, 42, 18, 51, 31, 56, 5, 36, 38,
01653     44, 4, 17, 26, 11, 38, 23, 42, 8, 56, 39, 24, 51, 5, 56, 21, 59, 14, 6,
01654     18, 42, 22, 35, 16, 37, 3, 25, 39, 46, 63, 5, 50, 17, 58, 8, 55, 3, 50,
01655     12, 43, 17, 47, 2, 51, 9, 62, 12, 1, 35, 13, 50, 1, 37, 12, 51, 19, 29,
01656     46, 59, 22, 58, 33, 45, 22, 60, 10, 32, 61, 39, 8, 33, 25, 36, 20, 60,
01657     38, 4, 21, 5, 28, 45, 12, 18, 42, 11, 49, 1, 27, 40, 6, 30},
01658    {24, 16, 42, 1, 50, 10, 48, 17, 33, 43, 24, 48, 21, 55, 31, 42, 10, 21,
01659     63, 35, 49, 6, 33, 13, 41, 53, 10, 20, 60, 6, 53, 26, 12, 41, 22, 60,
01660     14, 28, 63, 33, 49, 3, 45, 16, 48, 26, 14, 46, 18, 30, 35, 26, 8, 50,
01661     29, 51, 25, 57, 12, 47, 53, 9, 62, 20, 54, 2, 36, 15, 40, 28, 33, 13,
01662     38, 24, 46, 1, 29, 56, 33, 20, 44, 24, 41, 26, 57, 20, 63, 8, 30, 55,
01663     5, 41, 62, 8, 34, 2, 37, 10, 19, 6, 37, 1, 53, 23, 5, 27, 58, 22, 43,
01664     12, 50, 26, 9, 34, 54, 32, 49, 1, 59, 37, 22, 46, 25, 36, 51, 15, 54,
01665     46},
01666    {52, 7, 45, 33, 26, 58, 14, 60, 7, 54, 3, 58, 8, 34, 14, 5, 59, 30, 18,
01667     44, 8, 22, 48, 62, 3, 26, 55, 38, 23, 16, 39, 1, 62, 24, 49, 9, 53, 19,
01668     46, 7, 19, 60, 31, 58, 2, 34, 53, 7, 59, 2, 62, 42, 46, 19, 36, 11, 44,
01669     4, 38, 28, 1, 43, 32, 51, 12, 29, 56, 22, 52, 2, 62, 49, 22, 60, 14,
01670     35, 63, 5, 25, 57, 14, 53, 4, 46, 18, 31, 42, 22, 47, 20, 58, 31, 16,
01671     43, 23, 54, 30, 42, 52, 57, 29, 49, 30, 13, 45, 48, 16, 55, 6, 63, 1,
01672     44, 14, 58, 19, 47, 15, 24, 51, 34, 6, 55, 5, 63, 20, 41, 21, 9},
01673    {30, 62, 18, 55, 5, 23, 39, 29, 49, 30, 15, 36, 28, 46, 60, 25, 39, 46,
01674     4, 32, 61, 40, 15, 30, 36, 45, 14, 2, 49, 33, 57, 45, 18, 32, 3, 45,
01675     30, 2, 35, 52, 40, 27, 13, 21, 38, 63, 20, 28, 37, 23, 16, 10, 13, 55,
01676     2, 62, 21, 32, 60, 17, 58, 23, 5, 40, 16, 48, 7, 45, 10, 26, 43, 19, 6,
01677     31, 52, 21, 39, 16, 48, 9, 37, 28, 36, 55, 7, 48, 3, 59, 15, 45, 25, 1,
01678     53, 13, 47, 7, 62, 15, 4, 25, 12, 41, 18, 60, 38, 11, 34, 19, 39, 31,
01679     29, 56, 23, 42, 3, 27, 60, 41, 8, 16, 61, 29, 43, 9, 32, 2, 60, 34},
01680    {3, 38, 13, 37, 52, 44, 2, 19, 12, 42, 63, 19, 40, 1, 20, 50, 12, 55,
01681     15, 56, 27, 1, 54, 11, 57, 18, 32, 63, 44, 4, 29, 13, 37, 61, 35, 16,
01682     42, 57, 12, 22, 6, 55, 43, 10, 50, 5, 44, 11, 48, 52, 34, 58, 28, 41,
01683     38, 30, 7, 52, 11, 49, 30, 14, 45, 27, 59, 34, 21, 38, 32, 58, 11, 36,
01684     56, 42, 9, 41, 3, 54, 31, 42, 0, 60, 16, 11, 39, 24, 52, 33, 6, 36, 10,
01685     40, 32, 60, 26, 20, 39, 28, 47, 34, 63, 8, 54, 3, 24, 56, 0, 51, 13,
01686     47, 16, 40, 7, 35, 52, 11, 36, 4, 57, 30, 39, 13, 18, 50, 58, 28, 12,
01687     48},
01688    {57, 24, 49, 21, 10, 31, 61, 36, 56, 0, 22, 53, 11, 56, 32, 7, 36, 27,
01689     41, 9, 46, 19, 34, 42, 25, 7, 50, 9, 28, 21, 54, 8, 50, 7, 27, 59, 10,
01690     25, 48, 62, 37, 0, 33, 58, 25, 18, 32, 61, 0, 15, 45, 5, 50, 3, 23, 55,
01691     47, 17, 40, 6, 60, 34, 53, 8, 41, 0, 61, 13, 54, 4, 46, 28, 0, 17, 48,
01692     27, 58, 13, 23, 61, 33, 21, 50, 30, 62, 8, 14, 29, 56, 27, 61, 49, 17,
01693     2, 44, 11, 51, 0, 59, 17, 40, 20, 32, 47, 36, 21, 42, 28, 60, 4, 54,
01694     10, 59, 17, 30, 62, 21, 43, 26, 48, 0, 56, 36, 25, 8, 44, 39, 17},
01695    {10, 42, 4, 59, 27, 47, 8, 23, 51, 32, 45, 6, 37, 26, 48, 43, 62, 0, 21,
01696     53, 38, 12, 51, 5, 60, 47, 24, 37, 59, 15, 35, 47, 22, 55, 0, 50, 21,
01697     40, 6, 29, 15, 52, 24, 8, 41, 55, 13, 29, 40, 56, 24, 31, 19, 33, 61,
01698     15, 0, 35, 24, 42, 21, 2, 19, 57, 24, 15, 30, 50, 20, 25, 40, 16, 57,
01699     34, 61, 8, 29, 45, 6, 49, 11, 47, 2, 44, 19, 57, 38, 50, 12, 42, 21, 4,
01700     35, 52, 28, 56, 23, 36, 13, 45, 4, 52, 27, 14, 6, 62, 9, 45, 21, 37,
01701     25, 46, 33, 49, 0, 44, 7, 53, 13, 19, 53, 31, 3, 47, 15, 56, 22, 51},
01702    {35, 28, 53, 32, 1, 16, 54, 40, 9, 17, 25, 58, 14, 59, 3, 22, 16, 51,
01703     31, 5, 23, 58, 28, 17, 35, 20, 0, 42, 11, 52, 3, 31, 41, 17, 43, 13,
01704     32, 54, 18, 60, 32, 45, 17, 49, 2, 36, 51, 22, 7, 36, 9, 63, 48, 12,
01705     46, 26, 43, 28, 63, 13, 48, 37, 51, 33, 5, 47, 55, 9, 42, 63, 7, 51,
01706     24, 12, 37, 19, 55, 34, 18, 38, 15, 28, 54, 34, 5, 43, 22, 0, 48, 14,
01707     54, 24, 58, 9, 38, 5, 32, 55, 21, 30, 49, 9, 59, 43, 30, 51, 35, 26, 7,
01708     53, 2, 22, 14, 27, 57, 18, 38, 24, 33, 45, 10, 41, 20, 60, 37, 5, 32,
01709     0},
01710    {63, 19, 15, 40, 62, 35, 14, 28, 46, 61, 4, 49, 35, 10, 29, 54, 33, 8,
01711     45, 62, 37, 1, 43, 55, 10, 52, 61, 30, 19, 40, 25, 62, 11, 38, 27, 58,
01712     36, 3, 46, 8, 39, 4, 62, 28, 47, 20, 4, 54, 47, 27, 43, 1, 21, 38, 8,
01713     58, 10, 54, 4, 56, 9, 26, 12, 39, 60, 27, 18, 37, 1, 31, 35, 5, 45, 50,
01714     2, 43, 26, 1, 59, 23, 56, 40, 7, 26, 58, 17, 32, 63, 25, 39, 7, 31, 45,
01715     19, 63, 15, 48, 8, 37, 61, 16, 34, 1, 56, 18, 3, 15, 58, 49, 32, 63,
01716     41, 55, 5, 40, 22, 50, 6, 59, 2, 63, 23, 52, 11, 26, 61, 44, 23},
01717    {11, 56, 46, 6, 22, 43, 58, 3, 34, 21, 38, 30, 18, 44, 52, 13, 41, 57,
01718     17, 28, 14, 49, 25, 7, 33, 39, 26, 6, 56, 48, 1, 20, 56, 5, 46, 9, 19,
01719     51, 30, 25, 56, 21, 35, 14, 57, 42, 16, 33, 10, 57, 17, 59, 41, 25, 53,
01720     37, 20, 40, 30, 18, 31, 62, 44, 22, 3, 44, 11, 48, 23, 53, 18, 60, 29,
01721     22, 62, 15, 53, 47, 10, 41, 3, 19, 52, 36, 13, 46, 10, 35, 3, 61, 41,
01722     16, 1, 50, 26, 42, 18, 46, 2, 25, 54, 20, 39, 23, 47, 31, 41, 12, 38,
01723     17, 8, 19, 31, 48, 12, 61, 9, 54, 29, 35, 15, 38, 6, 43, 34, 14, 7,
01724     47},
01725    {39, 2, 33, 26, 53, 8, 18, 50, 41, 12, 53, 1, 63, 24, 19, 39, 2, 24, 47,
01726     10, 60, 38, 19, 63, 48, 4, 15, 45, 32, 14, 60, 36, 29, 53, 23, 63, 34,
01727     12, 61, 1, 43, 11, 53, 30, 1, 26, 60, 45, 23, 39, 3, 29, 12, 50, 4, 16,
01728     51, 3, 45, 36, 50, 1, 16, 54, 35, 14, 57, 30, 58, 9, 46, 14, 41, 10,
01729     32, 38, 4, 30, 21, 51, 32, 63, 25, 1, 60, 27, 53, 18, 51, 22, 28, 55,
01730     34, 12, 40, 3, 60, 29, 57, 41, 6, 44, 11, 53, 8, 61, 24, 57, 1, 28, 44,
01731     59, 36, 3, 34, 25, 41, 31, 16, 44, 22, 47, 28, 58, 1, 49, 54, 29},
01732    {58, 25, 50, 13, 38, 30, 60, 24, 6, 57, 27, 42, 9, 45, 6, 61, 30, 50, 4,
01733     34, 29, 3, 46, 13, 22, 42, 58, 28, 9, 39, 23, 44, 7, 15, 44, 2, 40, 15,
01734     47, 41, 23, 37, 7, 59, 38, 11, 34, 6, 62, 14, 52, 35, 55, 19, 32, 61,
01735     33, 24, 57, 6, 22, 59, 29, 7, 49, 25, 40, 3, 17, 39, 27, 52, 0, 55, 16,
01736     57, 24, 61, 36, 6, 29, 12, 48, 39, 20, 44, 6, 40, 33, 5, 48, 10, 57,
01737     36, 22, 51, 33, 9, 24, 12, 62, 29, 50, 35, 14, 43, 5, 33, 47, 52, 13,
01738     23, 10, 51, 56, 16, 46, 1, 49, 4, 61, 9, 52, 18, 31, 21, 36, 17},
01739    {19, 42, 9, 48, 2, 44, 11, 37, 48, 20, 33, 16, 55, 35, 49, 15, 37, 20,
01740     59, 16, 53, 22, 56, 31, 50, 11, 34, 54, 16, 51, 4, 49, 33, 53, 21, 28,
01741     56, 24, 31, 9, 52, 16, 48, 24, 44, 13, 51, 20, 31, 49, 18, 6, 34, 2,
01742     44, 14, 47, 8, 15, 43, 13, 41, 33, 52, 20, 61, 7, 51, 34, 62, 4, 20,
01743     36, 33, 43, 8, 46, 13, 53, 17, 45, 42, 9, 31, 52, 11, 30, 56, 13, 59,
01744     17, 44, 27, 6, 62, 11, 43, 17, 49, 38, 26, 2, 16, 27, 58, 21, 54, 18,
01745     26, 5, 35, 61, 43, 27, 7, 39, 14, 58, 37, 55, 20, 33, 13, 40, 62, 10,
01746     55, 5},
01747    {51, 14, 61, 29, 59, 20, 55, 31, 0, 49, 11, 60, 3, 26, 22, 56, 0, 40,
01748     12, 43, 41, 8, 36, 0, 17, 57, 24, 2, 46, 26, 61, 18, 0, 38, 12, 59, 6,
01749     49, 3, 57, 19, 63, 5, 33, 18, 54, 28, 56, 0, 43, 26, 46, 63, 27, 56,
01750     22, 27, 54, 38, 28, 63, 24, 10, 45, 0, 31, 42, 21, 12, 25, 44, 49, 59,
01751     6, 26, 50, 3, 34, 27, 59, 0, 35, 62, 16, 4, 58, 47, 0, 43, 24, 37, 2,
01752     54, 20, 46, 31, 0, 56, 34, 5, 55, 45, 60, 37, 0, 40, 10, 38, 63, 46,
01753     15, 20, 0, 53, 21, 62, 30, 11, 24, 27, 40, 0, 57, 26, 3, 45, 27, 35},
01754 };
01755 
01756 #else
01757 #define DM_WIDTH 8
01758 #define DM_WIDTH_SHIFT 3
01759 #define DM_HEIGHT 8
01760 static const guchar DM[8][8] = {
01761    {0, 32, 8, 40, 2, 34, 10, 42},
01762    {48, 16, 56, 24, 50, 18, 58, 26},
01763    {12, 44, 4, 36, 14, 46, 6, 38},
01764    {60, 28, 52, 20, 62, 30, 54, 22},
01765    {3, 35, 11, 43, 1, 33, 9, 41},
01766    {51, 19, 59, 27, 49, 17, 57, 25},
01767    {15, 47, 7, 39, 13, 45, 5, 37},
01768    {63, 31, 55, 23, 61, 29, 53, 21}
01769 };
01770 #endif
01771 
01772 static guint32 *DM_565 = NULL;
01773 
01774 static void gdk_rgb_preprocess_dm_565(void)
01775 {
01776    int i;
01777    guint32 dith;
01778 
01779    if (DM_565 == NULL) {
01780       DM_565 = g_new(guint32, DM_WIDTH * DM_HEIGHT);
01781       for (i = 0; i < DM_WIDTH * DM_HEIGHT; i++) {
01782          dith = DM[0][i] >> 3;
01783          DM_565[i] = (dith << 20) | dith | (((7 - dith) >> 1) << 10);
01784 #ifdef VERBOSE
01785          g_print("%i %x %x\n", i, dith, DM_565[i]);
01786 #endif
01787       }
01788    }
01789 }
01790 
01791 static void
01792 gdk_rgb_convert_8_d666(GdkImage * image,
01793                        gint x0, gint y0, gint width, gint height,
01794                        guchar * buf, int rowstride,
01795                        gint x_align, gint y_align, GdkRgbCmap * cmap)
01796 {
01797    int x, y;
01798    gint bpl;
01799    guchar *obuf, *obptr;
01800    guchar *bptr, *bp2;
01801    gint r, g, b;
01802    const guchar *dmp;
01803    gint dith;
01804 
01805    bptr = buf;
01806    bpl = image->bpl;
01807    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
01808    for (y = 0; y < height; y++) {
01809       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
01810       bp2 = bptr;
01811       obptr = obuf;
01812       for (x = 0; x < width; x++) {
01813          r = *bp2++;
01814          g = *bp2++;
01815          b = *bp2++;
01816          dith = (dmp[(x_align + x) & (DM_WIDTH - 1)] << 2) | 7;
01817          r = ((r * 5) + dith) >> 8;
01818          g = ((g * 5) + (262 - dith)) >> 8;
01819          b = ((b * 5) + dith) >> 8;
01820          obptr[0] = colorcube_d[(r << 6) | (g << 3) | b];
01821          obptr++;
01822       }
01823       bptr += rowstride;
01824       obuf += bpl;
01825    }
01826 }
01827 
01828 static void
01829 gdk_rgb_convert_8_d(GdkImage * image,
01830                     gint x0, gint y0, gint width, gint height,
01831                     guchar * buf, int rowstride,
01832                     gint x_align, gint y_align, GdkRgbCmap * cmap)
01833 {
01834    int x, y;
01835    gint bpl;
01836    guchar *obuf, *obptr;
01837    guchar *bptr, *bp2;
01838    gint r, g, b;
01839    const guchar *dmp;
01840    gint dith;
01841    gint rs, gs, bs;
01842 
01843    bptr = buf;
01844    bpl = image->bpl;
01845    rs = image_info->nred_shades - 1;
01846    gs = image_info->ngreen_shades - 1;
01847    bs = image_info->nblue_shades - 1;
01848    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
01849    for (y = 0; y < height; y++) {
01850       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
01851       bp2 = bptr;
01852       obptr = obuf;
01853       for (x = 0; x < width; x++) {
01854          r = *bp2++;
01855          g = *bp2++;
01856          b = *bp2++;
01857          dith = (dmp[(x_align + x) & (DM_WIDTH - 1)] << 2) | 7;
01858          r = ((r * rs) + dith) >> 8;
01859          g = ((g * gs) + (262 - dith)) >> 8;
01860          b = ((b * bs) + dith) >> 8;
01861          obptr[0] = colorcube_d[(r << 6) | (g << 3) | b];
01862          obptr++;
01863       }
01864       bptr += rowstride;
01865       obuf += bpl;
01866    }
01867 }
01868 
01869 static void
01870 gdk_rgb_convert_8_indexed(GdkImage * image,
01871                           gint x0, gint y0, gint width, gint height,
01872                           guchar * buf, int rowstride,
01873                           gint x_align, gint y_align, GdkRgbCmap * cmap)
01874 {
01875    int x, y;
01876    gint bpl;
01877    guchar *obuf, *obptr;
01878    guchar *bptr, *bp2;
01879    guchar c;
01880    guchar *lut;
01881 
01882    lut = cmap->lut;
01883    bptr = buf;
01884    bpl = image->bpl;
01885    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
01886    for (y = 0; y < height; y++) {
01887       bp2 = bptr;
01888       obptr = obuf;
01889       for (x = 0; x < width; x++) {
01890          c = *bp2++;
01891          obptr[0] = lut[c];
01892          obptr++;
01893       }
01894       bptr += rowstride;
01895       obuf += bpl;
01896    }
01897 }
01898 
01899 static void
01900 gdk_rgb_convert_gray8(GdkImage * image,
01901                       gint x0, gint y0, gint width, gint height,
01902                       guchar * buf, int rowstride,
01903                       gint x_align, gint y_align, GdkRgbCmap * cmap)
01904 {
01905    int x, y;
01906    gint bpl;
01907    guchar *obuf, *obptr;
01908    guchar *bptr, *bp2;
01909    gint r, g, b;
01910 
01911    bptr = buf;
01912    bpl = image->bpl;
01913    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
01914    for (y = 0; y < height; y++) {
01915       bp2 = bptr;
01916       obptr = obuf;
01917       for (x = 0; x < width; x++) {
01918          r = *bp2++;
01919          g = *bp2++;
01920          b = *bp2++;
01921          obptr[0] = (g + ((b + r) >> 1)) >> 1;
01922          obptr++;
01923       }
01924       bptr += rowstride;
01925       obuf += bpl;
01926    }
01927 }
01928 
01929 static void
01930 gdk_rgb_convert_gray8_gray(GdkImage * image,
01931                            gint x0, gint y0, gint width, gint height,
01932                            guchar * buf, int rowstride,
01933                            gint x_align, gint y_align, GdkRgbCmap * cmap)
01934 {
01935    int y;
01936    gint bpl;
01937    guchar *obuf;
01938    guchar *bptr;
01939 
01940    bptr = buf;
01941    bpl = image->bpl;
01942    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
01943    for (y = 0; y < height; y++) {
01944       memcpy(obuf, bptr, width);
01945       bptr += rowstride;
01946       obuf += bpl;
01947    }
01948 }
01949 
01950 #if G_BYTE_ORDER == G_LITTLE_ENDIAN
01951 #define HAIRY_CONVERT_565
01952 #endif
01953 
01954 #ifdef HAIRY_CONVERT_565
01955 /* Render a 24-bit RGB image in buf into the GdkImage, without dithering.
01956    This assumes native byte ordering - what should really be done is to
01957    check whether static_image->byte_order is consistent with the _ENDIAN
01958    config flag, and if not, use a different function.
01959 
01960    This one is even faster than the one below - its inner loop loads 3
01961    words (i.e. 4 24-bit pixels), does a lot of shifting and masking,
01962    then writes 2 words. */
01963 static void
01964 gdk_rgb_convert_565(GdkImage * image,
01965                     gint x0, gint y0, gint width, gint height,
01966                     guchar * buf, int rowstride,
01967                     gint x_align, gint y_align, GdkRgbCmap * cmap)
01968 {
01969    int x, y;
01970    guchar *obuf, *obptr;
01971    gint bpl;
01972    guchar *bptr, *bp2;
01973    guchar r, g, b;
01974 
01975    bptr = buf;
01976    bpl = image->bpl;
01977    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
01978    for (y = 0; y < height; y++) {
01979       bp2 = bptr;
01980       obptr = obuf;
01981       if (((unsigned long) obuf | (unsigned long) bp2) & 3) {
01982          for (x = 0; x < width; x++) {
01983             r = *bp2++;
01984             g = *bp2++;
01985             b = *bp2++;
01986             ((guint16 *) obptr)[0] = ((r & 0xf8) << 8) |
01987                 ((g & 0xfc) << 3) | (b >> 3);
01988             obptr += 2;
01989          }
01990       } else {
01991          for (x = 0; x < width - 3; x += 4) {
01992             guint32 r1b0g0r0;
01993             guint32 g2r2b1g1;
01994             guint32 b3g3r3b2;
01995 
01996             r1b0g0r0 = ((guint32 *) bp2)[0];
01997             g2r2b1g1 = ((guint32 *) bp2)[1];
01998             b3g3r3b2 = ((guint32 *) bp2)[2];
01999             ((guint32 *) obptr)[0] =
02000                 ((r1b0g0r0 & 0xf8) << 8) |
02001                 ((r1b0g0r0 & 0xfc00) >> 5) |
02002                 ((r1b0g0r0 & 0xf80000) >> 19) |
02003                 (r1b0g0r0 & 0xf8000000) |
02004                 ((g2r2b1g1 & 0xfc) << 19) | ((g2r2b1g1 & 0xf800) << 5);
02005             ((guint32 *) obptr)[1] =
02006                 ((g2r2b1g1 & 0xf80000) >> 8) |
02007                 ((g2r2b1g1 & 0xfc000000) >> 21) |
02008                 ((b3g3r3b2 & 0xf8) >> 3) |
02009                 ((b3g3r3b2 & 0xf800) << 16) |
02010                 ((b3g3r3b2 & 0xfc0000) << 3) |
02011                 ((b3g3r3b2 & 0xf8000000) >> 11);
02012             bp2 += 12;
02013             obptr += 8;
02014          }
02015          for (; x < width; x++) {
02016             r = *bp2++;
02017             g = *bp2++;
02018             b = *bp2++;
02019             ((guint16 *) obptr)[0] = ((r & 0xf8) << 8) |
02020                 ((g & 0xfc) << 3) | (b >> 3);
02021             obptr += 2;
02022          }
02023       }
02024       bptr += rowstride;
02025       obuf += bpl;
02026    }
02027 }
02028 #else
02029 /* Render a 24-bit RGB image in buf into the GdkImage, without dithering.
02030    This assumes native byte ordering - what should really be done is to
02031    check whether static_image->byte_order is consistent with the _ENDIAN
02032    config flag, and if not, use a different function.
02033 
02034    This routine is faster than the one included with Gtk 1.0 for a number
02035    of reasons:
02036 
02037    1. Shifting instead of lookup tables (less memory traffic).
02038 
02039    2. Much less register pressure, especially because shifts are
02040    in the code.
02041 
02042    3. A memcpy is avoided (i.e. the transfer function).
02043 
02044    4. On big-endian architectures, byte swapping is avoided.
02045 
02046    That said, it wouldn't be hard to make it even faster - just make an
02047    inner loop that reads 3 words (i.e. 4 24-bit pixels), does a lot of
02048    shifting and masking, then writes 2 words.
02049 */
02050 static void
02051 gdk_rgb_convert_565(GdkImage * image,
02052                     gint x0, gint y0, gint width, gint height,
02053                     guchar * buf, int rowstride,
02054                     gint x_align, gint y_align, GdkRgbCmap * cmap)
02055 {
02056    int x, y;
02057    guchar *obuf;
02058    gint bpl;
02059    guchar *bptr, *bp2;
02060    guchar r, g, b;
02061 
02062    bptr = buf;
02063    bpl = image->bpl;
02064    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
02065    for (y = 0; y < height; y++) {
02066       bp2 = bptr;
02067       for (x = 0; x < width; x++) {
02068          r = *bp2++;
02069          g = *bp2++;
02070          b = *bp2++;
02071          ((unsigned short *) obuf)[x] = ((r & 0xf8) << 8) |
02072              ((g & 0xfc) << 3) | (b >> 3);
02073       }
02074       bptr += rowstride;
02075       obuf += bpl;
02076    }
02077 }
02078 #endif
02079 
02080 #ifdef HAIRY_CONVERT_565
02081 static void
02082 gdk_rgb_convert_565_gray(GdkImage * image,
02083                          gint x0, gint y0, gint width, gint height,
02084                          guchar * buf, int rowstride,
02085                          gint x_align, gint y_align, GdkRgbCmap * cmap)
02086 {
02087    int x, y;
02088    guchar *obuf, *obptr;
02089    gint bpl;
02090    guchar *bptr, *bp2;
02091    guchar g;
02092 
02093    bptr = buf;
02094    bpl = image->bpl;
02095    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
02096    for (y = 0; y < height; y++) {
02097       bp2 = bptr;
02098       obptr = obuf;
02099       if (((unsigned long) obuf | (unsigned long) bp2) & 3) {
02100          for (x = 0; x < width; x++) {
02101             g = *bp2++;
02102             ((guint16 *) obptr)[0] = ((g & 0xf8) << 8) |
02103                 ((g & 0xfc) << 3) | (g >> 3);
02104             obptr += 2;
02105          }
02106       } else {
02107          for (x = 0; x < width - 3; x += 4) {
02108             guint32 g3g2g1g0;
02109 
02110             g3g2g1g0 = ((guint32 *) bp2)[0];
02111             ((guint32 *) obptr)[0] =
02112                 ((g3g2g1g0 & 0xf8) << 8) |
02113                 ((g3g2g1g0 & 0xfc) << 3) |
02114                 ((g3g2g1g0 & 0xf8) >> 3) |
02115                 (g3g2g1g0 & 0xf800) << 16 |
02116                 ((g3g2g1g0 & 0xfc00) << 11) | ((g3g2g1g0 & 0xf800) << 5);
02117             ((guint32 *) obptr)[1] =
02118                 ((g3g2g1g0 & 0xf80000) >> 8) |
02119                 ((g3g2g1g0 & 0xfc0000) >> 13) |
02120                 ((g3g2g1g0 & 0xf80000) >> 19) |
02121                 (g3g2g1g0 & 0xf8000000) |
02122                 ((g3g2g1g0 & 0xfc000000) >> 5) |
02123                 ((g3g2g1g0 & 0xf8000000) >> 11);
02124             bp2 += 4;
02125             obptr += 8;
02126          }
02127          for (; x < width; x++) {
02128             g = *bp2++;
02129             ((guint16 *) obptr)[0] = ((g & 0xf8) << 8) |
02130                 ((g & 0xfc) << 3) | (g >> 3);
02131             obptr += 2;
02132          }
02133       }
02134       bptr += rowstride;
02135       obuf += bpl;
02136    }
02137 }
02138 #else
02139 static void
02140 gdk_rgb_convert_565_gray(GdkImage * image,
02141                          gint x0, gint y0, gint width, gint height,
02142                          guchar * buf, int rowstride,
02143                          gint x_align, gint y_align, GdkRgbCmap * cmap)
02144 {
02145    int x, y;
02146    guchar *obuf;
02147    gint bpl;
02148    guchar *bptr, *bp2;
02149    guchar g;
02150 
02151    bptr = buf;
02152    bpl = image->bpl;
02153    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
02154    for (y = 0; y < height; y++) {
02155       bp2 = bptr;
02156       for (x = 0; x < width; x++) {
02157          g = *bp2++;
02158          ((guint16 *) obuf)[x] = ((g & 0xf8) << 8) |
02159              ((g & 0xfc) << 3) | (g >> 3);
02160       }
02161       bptr += rowstride;
02162       obuf += bpl;
02163    }
02164 }
02165 #endif
02166 
02167 static void
02168 gdk_rgb_convert_565_br(GdkImage * image,
02169                        gint x0, gint y0, gint width, gint height,
02170                        guchar * buf, int rowstride,
02171                        gint x_align, gint y_align, GdkRgbCmap * cmap)
02172 {
02173    int x, y;
02174    guchar *obuf;
02175    gint bpl;
02176    guchar *bptr, *bp2;
02177    guchar r, g, b;
02178 
02179    bptr = buf;
02180    bpl = image->bpl;
02181    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
02182    for (y = 0; y < height; y++) {
02183       bp2 = bptr;
02184       for (x = 0; x < width; x++) {
02185          r = *bp2++;
02186          g = *bp2++;
02187          b = *bp2++;
02188          /* final word is:
02189             g4 g3 g2 b7 b6 b5 b4 b3  r7 r6 r5 r4 r3 g7 g6 g5
02190           */
02191          ((unsigned short *) obuf)[x] = (r & 0xf8) |
02192              ((g & 0xe0) >> 5) | ((g & 0x1c) << 11) | ((b & 0xf8) << 5);
02193       }
02194       bptr += rowstride;
02195       obuf += bpl;
02196    }
02197 }
02198 
02199 /* Thanks to Ray Lehtiniemi for a patch that resulted in a ~25% speedup
02200    in this mode. */
02201 #ifdef HAIRY_CONVERT_565
02202 static void
02203 gdk_rgb_convert_565_d(GdkImage * image,
02204                       gint x0, gint y0, gint width, gint height,
02205                       guchar * buf, int rowstride,
02206                       gint x_align, gint y_align, GdkRgbCmap * cmap)
02207 {
02208    /* Now this is what I'd call some highly tuned code! */
02209    int x, y;
02210    guchar *obuf, *obptr;
02211    gint bpl;
02212    guchar *bptr, *bp2;
02213 
02214    width += x_align;
02215    height += y_align;
02216 
02217    bptr = buf;
02218    bpl = image->bpl;
02219    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
02220    for (y = y_align; y < height; y++) {
02221       guint32 *dmp = DM_565 + ((y & (DM_HEIGHT - 1)) << DM_WIDTH_SHIFT);
02222       bp2 = bptr;
02223       obptr = obuf;
02224       if (((unsigned long) obuf | (unsigned long) bp2) & 3) {
02225          for (x = x_align; x < width; x++) {
02226             gint32 rgb = *bp2++ << 20;
02227             rgb += *bp2++ << 10;
02228             rgb += *bp2++;
02229             rgb += dmp[x & (DM_WIDTH - 1)];
02230             rgb += 0x10040100 - ((rgb & 0x1e0001e0) >> 5)
02231                 - ((rgb & 0x00070000) >> 6);
02232 
02233             ((unsigned short *) obptr)[0] =
02234                 ((rgb & 0x0f800000) >> 12) |
02235                 ((rgb & 0x0003f000) >> 7) | ((rgb & 0x000000f8) >> 3);
02236             obptr += 2;
02237          }
02238       } else {
02239          for (x = x_align; x < width - 3; x += 4) {
02240             guint32 r1b0g0r0;
02241             guint32 g2r2b1g1;
02242             guint32 b3g3r3b2;
02243             guint32 rgb02, rgb13;
02244 
02245             r1b0g0r0 = ((guint32 *) bp2)[0];
02246             g2r2b1g1 = ((guint32 *) bp2)[1];
02247             b3g3r3b2 = ((guint32 *) bp2)[2];
02248             rgb02 =
02249                 ((r1b0g0r0 & 0xff) << 20) +
02250                 ((r1b0g0r0 & 0xff00) << 2) +
02251                 ((r1b0g0r0 & 0xff0000) >> 16) + dmp[x & (DM_WIDTH - 1)];
02252             rgb02 += 0x10040100 - ((rgb02 & 0x1e0001e0) >> 5)
02253                 - ((rgb02 & 0x00070000) >> 6);
02254             rgb13 =
02255                 ((r1b0g0r0 & 0xff000000) >> 4) +
02256                 ((g2r2b1g1 & 0xff) << 10) +
02257                 ((g2r2b1g1 & 0xff00) >> 8) + dmp[(x + 1) & (DM_WIDTH - 1)];
02258             rgb13 += 0x10040100 - ((rgb13 & 0x1e0001e0) >> 5)
02259                 - ((rgb13 & 0x00070000) >> 6);
02260             ((guint32 *) obptr)[0] =
02261                 ((rgb02 & 0x0f800000) >> 12) |
02262                 ((rgb02 & 0x0003f000) >> 7) |
02263                 ((rgb02 & 0x000000f8) >> 3) |
02264                 ((rgb13 & 0x0f800000) << 4) |
02265                 ((rgb13 & 0x0003f000) << 9) | ((rgb13 & 0x000000f8) << 13);
02266             rgb02 =
02267                 ((g2r2b1g1 & 0xff0000) << 4) +
02268                 ((g2r2b1g1 & 0xff000000) >> 14) +
02269                 (b3g3r3b2 & 0xff) + dmp[(x + 2) & (DM_WIDTH - 1)];
02270             rgb02 += 0x10040100 - ((rgb02 & 0x1e0001e0) >> 5)
02271                 - ((rgb02 & 0x00070000) >> 6);
02272             rgb13 =
02273                 ((b3g3r3b2 & 0xff00) << 12) +
02274                 ((b3g3r3b2 & 0xff0000) >> 6) +
02275                 ((b3g3r3b2 & 0xff000000) >> 24) +
02276                 dmp[(x + 3) & (DM_WIDTH - 1)];
02277             rgb13 += 0x10040100 - ((rgb13 & 0x1e0001e0) >> 5)
02278                 - ((rgb13 & 0x00070000) >> 6);
02279             ((guint32 *) obptr)[1] =
02280                 ((rgb02 & 0x0f800000) >> 12) |
02281                 ((rgb02 & 0x0003f000) >> 7) |
02282                 ((rgb02 & 0x000000f8) >> 3) |
02283                 ((rgb13 & 0x0f800000) << 4) |
02284                 ((rgb13 & 0x0003f000) << 9) | ((rgb13 & 0x000000f8) << 13);
02285             bp2 += 12;
02286             obptr += 8;
02287          }
02288          for (; x < width; x++) {
02289             gint32 rgb = *bp2++ << 20;
02290             rgb += *bp2++ << 10;
02291             rgb += *bp2++;
02292             rgb += dmp[x & (DM_WIDTH - 1)];
02293             rgb += 0x10040100 - ((rgb & 0x1e0001e0) >> 5)
02294                 - ((rgb & 0x00070000) >> 6);
02295 
02296             ((unsigned short *) obptr)[0] =
02297                 ((rgb & 0x0f800000) >> 12) |
02298                 ((rgb & 0x0003f000) >> 7) | ((rgb & 0x000000f8) >> 3);
02299             obptr += 2;
02300          }
02301       }
02302       bptr += rowstride;
02303       obuf += bpl;
02304    }
02305 }
02306 #else
02307 static void
02308 gdk_rgb_convert_565_d(GdkImage * image,
02309                       gint x0, gint y0, gint width, gint height,
02310                       guchar * buf, int rowstride,
02311                       gint x_align, gint y_align, GdkRgbCmap * cmap)
02312 {
02313    int x, y;
02314    guchar *obuf;
02315    gint bpl;
02316    guchar *bptr;
02317 
02318    width += x_align;
02319    height += y_align;
02320 
02321    bptr = buf;
02322    bpl = image->bpl;
02323    obuf = ((guchar *) image->mem) + y0 * bpl + (x0 - x_align) * 2;
02324 
02325    for (y = y_align; y < height; y++) {
02326       guint32 *dmp = DM_565 + ((y & (DM_HEIGHT - 1)) << DM_WIDTH_SHIFT);
02327       guchar *bp2 = bptr;
02328 
02329       for (x = x_align; x < width; x++) {
02330          gint32 rgb = *bp2++ << 20;
02331          rgb += *bp2++ << 10;
02332          rgb += *bp2++;
02333          rgb += dmp[x & (DM_WIDTH - 1)];
02334          rgb += 0x10040100 - ((rgb & 0x1e0001e0) >> 5)
02335              - ((rgb & 0x00070000) >> 6);
02336 
02337          ((unsigned short *) obuf)[x] =
02338              ((rgb & 0x0f800000) >> 12) |
02339              ((rgb & 0x0003f000) >> 7) | ((rgb & 0x000000f8) >> 3);
02340       }
02341 
02342       bptr += rowstride;
02343       obuf += bpl;
02344    }
02345 }
02346 #endif
02347 
02348 static void
02349 gdk_rgb_convert_555(GdkImage * image,
02350                     gint x0, gint y0, gint width, gint height,
02351                     guchar * buf, int rowstride,
02352                     gint x_align, gint y_align, GdkRgbCmap * cmap)
02353 {
02354    int x, y;
02355    guchar *obuf;
02356    gint bpl;
02357    guchar *bptr, *bp2;
02358    guchar r, g, b;
02359 
02360    bptr = buf;
02361    bpl = image->bpl;
02362    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
02363    for (y = 0; y < height; y++) {
02364       bp2 = bptr;
02365       for (x = 0; x < width; x++) {
02366          r = *bp2++;
02367          g = *bp2++;
02368          b = *bp2++;
02369          ((unsigned short *) obuf)[x] = ((r & 0xf8) << 7) |
02370              ((g & 0xf8) << 2) | (b >> 3);
02371       }
02372       bptr += rowstride;
02373       obuf += bpl;
02374    }
02375 }
02376 
02377 static void
02378 gdk_rgb_convert_555_br(GdkImage * image,
02379                        gint x0, gint y0, gint width, gint height,
02380                        guchar * buf, int rowstride,
02381                        gint x_align, gint y_align, GdkRgbCmap * cmap)
02382 {
02383    int x, y;
02384    guchar *obuf;
02385    gint bpl;
02386    guchar *bptr, *bp2;
02387    guchar r, g, b;
02388 
02389    bptr = buf;
02390    bpl = image->bpl;
02391    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 2;
02392    for (y = 0; y < height; y++) {
02393       bp2 = bptr;
02394       for (x = 0; x < width; x++) {
02395          r = *bp2++;
02396          g = *bp2++;
02397          b = *bp2++;
02398          /* final word is:
02399             g5 g4 g3 b7 b6 b5 b4 b3  0 r7 r6 r5 r4 r3 g7 g6
02400           */
02401          ((unsigned short *) obuf)[x] = ((r & 0xf8) >> 1) |
02402              ((g & 0xc0) >> 6) | ((g & 0x18) << 10) | ((b & 0xf8) << 5);
02403       }
02404       bptr += rowstride;
02405       obuf += bpl;
02406    }
02407 }
02408 
02409 static void
02410 gdk_rgb_convert_888_msb(GdkImage * image,
02411                         gint x0, gint y0, gint width, gint height,
02412                         guchar * buf, int rowstride,
02413                         gint x_align, gint y_align, GdkRgbCmap * cmap)
02414 {
02415    int y;
02416    guchar *obuf;
02417    gint bpl;
02418    guchar *bptr;
02419 
02420    bptr = buf;
02421    bpl = image->bpl;
02422    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 3;
02423    for (y = 0; y < height; y++) {
02424       memcpy(obuf, bptr, width + width + width);
02425       bptr += rowstride;
02426       obuf += bpl;
02427    }
02428 }
02429 
02430 /* todo: optimize this */
02431 #if G_BYTE_ORDER == G_LITTLE_ENDIAN
02432 #define HAIRY_CONVERT_888
02433 #endif
02434 
02435 #ifdef HAIRY_CONVERT_888
02436 static void
02437 gdk_rgb_convert_888_lsb(GdkImage * image,
02438                         gint x0, gint y0, gint width, gint height,
02439                         guchar * buf, int rowstride,
02440                         gint x_align, gint y_align, GdkRgbCmap * cmap)
02441 {
02442    int x, y;
02443    guchar *obuf, *obptr;
02444    gint bpl;
02445    guchar *bptr, *bp2;
02446    int r, g, b;
02447 
02448    bptr = buf;
02449    bpl = image->bpl;
02450    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 3;
02451    for (y = 0; y < height; y++) {
02452       bp2 = bptr;
02453       obptr = obuf;
02454       if (((unsigned long) obuf | (unsigned long) bp2) & 3) {
02455          for (x = 0; x < width; x++) {
02456             r = bp2[0];
02457             g = bp2[1];
02458             b = bp2[2];
02459             *obptr++ = b;
02460             *obptr++ = g;
02461             *obptr++ = r;
02462             bp2 += 3;
02463          }
02464       } else {
02465          for (x = 0; x < width - 3; x += 4) {
02466             guint32 r1b0g0r0;
02467             guint32 g2r2b1g1;
02468             guint32 b3g3r3b2;
02469 
02470             r1b0g0r0 = ((guint32 *) bp2)[0];
02471             g2r2b1g1 = ((guint32 *) bp2)[1];
02472             b3g3r3b2 = ((guint32 *) bp2)[2];
02473             ((guint32 *) obptr)[0] =
02474                 (r1b0g0r0 & 0xff00) |
02475                 ((r1b0g0r0 & 0xff0000) >> 16) |
02476                 (((g2r2b1g1 & 0xff00) | (r1b0g0r0 & 0xff)) << 16);
02477             ((guint32 *) obptr)[1] =
02478                 (g2r2b1g1 & 0xff0000ff) |
02479                 ((r1b0g0r0 & 0xff000000) >> 16) |
02480                 ((b3g3r3b2 & 0xff) << 16);
02481             ((guint32 *) obptr)[2] =
02482                 (((g2r2b1g1 & 0xff0000) | (b3g3r3b2 & 0xff000000)) >> 16) |
02483                 ((b3g3r3b2 & 0xff00) << 16) | ((b3g3r3b2 & 0xff0000));
02484             bp2 += 12;
02485             obptr += 12;
02486          }
02487          for (; x < width; x++) {
02488             r = bp2[0];
02489             g = bp2[1];
02490             b = bp2[2];
02491             *obptr++ = b;
02492             *obptr++ = g;
02493             *obptr++ = r;
02494             bp2 += 3;
02495          }
02496       }
02497       bptr += rowstride;
02498       obuf += bpl;
02499    }
02500 }
02501 #else
02502 static void
02503 gdk_rgb_convert_888_lsb(GdkImage * image,
02504                         gint x0, gint y0, gint width, gint height,
02505                         guchar * buf, int rowstride,
02506                         gint x_align, gint y_align, GdkRgbCmap * cmap)
02507 {
02508    int x, y;
02509    guchar *obuf;
02510    gint bpl;
02511    guchar *bptr, *bp2;
02512    int r, g, b;
02513 
02514    bptr = buf;
02515    bpl = image->bpl;
02516    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 3;
02517    for (y = 0; y < height; y++) {
02518       bp2 = bptr;
02519       for (x = 0; x < width; x++) {
02520          r = bp2[0];
02521          g = bp2[1];
02522          b = bp2[2];
02523          obuf[x * 3] = b;
02524          obuf[x * 3 + 1] = g;
02525          obuf[x * 3 + 2] = r;
02526          bp2 += 3;
02527       }
02528       bptr += rowstride;
02529       obuf += bpl;
02530    }
02531 }
02532 #endif
02533 
02534 /* convert 24-bit packed to 32-bit unpacked */
02535 /* todo: optimize this */
02536 static void
02537 gdk_rgb_convert_0888(GdkImage * image,
02538                      gint x0, gint y0, gint width, gint height,
02539                      guchar * buf, int rowstride,
02540                      gint x_align, gint y_align, GdkRgbCmap * cmap)
02541 {
02542    int x, y;
02543    guchar *obuf;
02544    gint bpl;
02545    guchar *bptr, *bp2;
02546    int r, g, b;
02547 
02548    bptr = buf;
02549    bpl = image->bpl;
02550    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 4;
02551    for (y = 0; y < height; y++) {
02552       bp2 = bptr;
02553       for (x = 0; x < width; x++) {
02554          r = bp2[0];
02555          g = bp2[1];
02556          b = bp2[2];
02557          ((guint32 *) obuf)[x] = (r << 16) | (g << 8) | b;
02558          bp2 += 3;
02559       }
02560       bptr += rowstride;
02561       obuf += bpl;
02562    }
02563 }
02564 
02565 static void
02566 gdk_rgb_convert_0888_br(GdkImage * image,
02567                         gint x0, gint y0, gint width, gint height,
02568                         guchar * buf, int rowstride,
02569                         gint x_align, gint y_align, GdkRgbCmap * cmap)
02570 {
02571    int x, y;
02572    guchar *obuf;
02573    gint bpl;
02574    guchar *bptr, *bp2;
02575    int r, g, b;
02576 
02577    bptr = buf;
02578    bpl = image->bpl;
02579    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 4;
02580    for (y = 0; y < height; y++) {
02581       bp2 = bptr;
02582       for (x = 0; x < width; x++) {
02583          r = bp2[0];
02584          g = bp2[1];
02585          b = bp2[2];
02586          ((guint32 *) obuf)[x] = (b << 24) | (g << 16) | (r << 8);
02587          bp2 += 3;
02588       }
02589       bptr += rowstride;
02590       obuf += bpl;
02591    }
02592 }
02593 
02594 static void
02595 gdk_rgb_convert_8880_br(GdkImage * image,
02596                         gint x0, gint y0, gint width, gint height,
02597                         guchar * buf, int rowstride,
02598                         gint x_align, gint y_align, GdkRgbCmap * cmap)
02599 {
02600    int x, y;
02601    guchar *obuf;
02602    gint bpl;
02603    guchar *bptr, *bp2;
02604    int r, g, b;
02605 
02606    bptr = buf;
02607    bpl = image->bpl;
02608    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * 4;
02609    for (y = 0; y < height; y++) {
02610       bp2 = bptr;
02611       for (x = 0; x < width; x++) {
02612          r = bp2[0];
02613          g = bp2[1];
02614          b = bp2[2];
02615          ((guint32 *) obuf)[x] = (b << 16) | (g << 8) | r;
02616          bp2 += 3;
02617       }
02618       bptr += rowstride;
02619       obuf += bpl;
02620    }
02621 }
02622 
02623 /* Generic truecolor/directcolor conversion function. Slow, but these
02624    are oddball modes. */
02625 static void
02626 gdk_rgb_convert_truecolor_lsb(GdkImage * image,
02627                               gint x0, gint y0, gint width, gint height,
02628                               guchar * buf, int rowstride,
02629                               gint x_align, gint y_align,
02630                               GdkRgbCmap * cmap)
02631 {
02632    int x, y;
02633    guchar *obuf, *obptr;
02634    gint bpl;
02635    guchar *bptr, *bp2;
02636    gint r, g, b;
02637    gint r_right, r_left;
02638    gint g_right, g_left;
02639    gint b_right, b_left;
02640    gint bpp;
02641    guint32 pixel;
02642    gint i;
02643 
02644    r_right = 8 - image_info->visual->red_prec;
02645    r_left = image_info->visual->red_shift;
02646    g_right = 8 - image_info->visual->green_prec;
02647    g_left = image_info->visual->green_shift;
02648    b_right = 8 - image_info->visual->blue_prec;
02649    b_left = image_info->visual->blue_shift;
02650    bpp = image_info->bpp;
02651    bptr = buf;
02652    bpl = image->bpl;
02653    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * bpp;
02654    for (y = 0; y < height; y++) {
02655       obptr = obuf;
02656       bp2 = bptr;
02657       for (x = 0; x < width; x++) {
02658          r = bp2[0];
02659          g = bp2[1];
02660          b = bp2[2];
02661          pixel = ((r >> r_right) << r_left) |
02662              ((g >> g_right) << g_left) | ((b >> b_right) << b_left);
02663          for (i = 0; i < bpp; i++) {
02664             *obptr++ = pixel & 0xff;
02665             pixel >>= 8;
02666          }
02667          bp2 += 3;
02668       }
02669       bptr += rowstride;
02670       obuf += bpl;
02671    }
02672 }
02673 
02674 static void
02675 gdk_rgb_convert_truecolor_lsb_d(GdkImage * image,
02676                                 gint x0, gint y0, gint width, gint height,
02677                                 guchar * buf, int rowstride,
02678                                 gint x_align, gint y_align,
02679                                 GdkRgbCmap * cmap)
02680 {
02681    int x, y;
02682    guchar *obuf, *obptr;
02683    gint bpl;
02684    guchar *bptr, *bp2;
02685    gint r, g, b;
02686    gint r_right, r_left, r_prec;
02687    gint g_right, g_left, g_prec;
02688    gint b_right, b_left, b_prec;
02689    gint bpp;
02690    guint32 pixel;
02691    gint i;
02692    gint dith;
02693    gint r1, g1, b1;
02694    const guchar *dmp;
02695 
02696    r_right = 8 - image_info->visual->red_prec;
02697    r_left = image_info->visual->red_shift;
02698    r_prec = image_info->visual->red_prec;
02699    g_right = 8 - image_info->visual->green_prec;
02700    g_left = image_info->visual->green_shift;
02701    g_prec = image_info->visual->green_prec;
02702    b_right = 8 - image_info->visual->blue_prec;
02703    b_left = image_info->visual->blue_shift;
02704    b_prec = image_info->visual->blue_prec;
02705    bpp = image_info->bpp;
02706    bptr = buf;
02707    bpl = image->bpl;
02708    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * bpp;
02709    for (y = 0; y < height; y++) {
02710       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
02711       obptr = obuf;
02712       bp2 = bptr;
02713       for (x = 0; x < width; x++) {
02714          r = bp2[0];
02715          g = bp2[1];
02716          b = bp2[2];
02717          dith = dmp[(x_align + x) & (DM_WIDTH - 1)] << 2;
02718          r1 = r + (dith >> r_prec);
02719          g1 = g + ((252 - dith) >> g_prec);
02720          b1 = b + (dith >> b_prec);
02721          pixel = (((r1 - (r1 >> r_prec)) >> r_right) << r_left) |
02722              (((g1 - (g1 >> g_prec)) >> g_right) << g_left) |
02723              (((b1 - (b1 >> b_prec)) >> b_right) << b_left);
02724          for (i = 0; i < bpp; i++) {
02725             *obptr++ = pixel & 0xff;
02726             pixel >>= 8;
02727          }
02728          bp2 += 3;
02729       }
02730       bptr += rowstride;
02731       obuf += bpl;
02732    }
02733 }
02734 
02735 static void
02736 gdk_rgb_convert_truecolor_msb(GdkImage * image,
02737                               gint x0, gint y0, gint width, gint height,
02738                               guchar * buf, int rowstride,
02739                               gint x_align, gint y_align,
02740                               GdkRgbCmap * cmap)
02741 {
02742    int x, y;
02743    guchar *obuf, *obptr;
02744    gint bpl;
02745    guchar *bptr, *bp2;
02746    gint r, g, b;
02747    gint r_right, r_left;
02748    gint g_right, g_left;
02749    gint b_right, b_left;
02750    gint bpp;
02751    guint32 pixel;
02752    gint shift, shift_init;
02753 
02754    r_right = 8 - image_info->visual->red_prec;
02755    r_left = image_info->visual->red_shift;
02756    g_right = 8 - image_info->visual->green_prec;
02757    g_left = image_info->visual->green_shift;
02758    b_right = 8 - image_info->visual->blue_prec;
02759    b_left = image_info->visual->blue_shift;
02760    bpp = image_info->bpp;
02761    bptr = buf;
02762    bpl = image->bpl;
02763    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * bpp;
02764    shift_init = (bpp - 1) << 3;
02765    for (y = 0; y < height; y++) {
02766       obptr = obuf;
02767       bp2 = bptr;
02768       for (x = 0; x < width; x++) {
02769          r = bp2[0];
02770          g = bp2[1];
02771          b = bp2[2];
02772          pixel = ((r >> r_right) << r_left) |
02773              ((g >> g_right) << g_left) | ((b >> b_right) << b_left);
02774          for (shift = shift_init; shift >= 0; shift -= 8) {
02775             *obptr++ = (pixel >> shift) & 0xff;
02776          }
02777          bp2 += 3;
02778       }
02779       bptr += rowstride;
02780       obuf += bpl;
02781    }
02782 }
02783 
02784 static void
02785 gdk_rgb_convert_truecolor_msb_d(GdkImage * image,
02786                                 gint x0, gint y0, gint width, gint height,
02787                                 guchar * buf, int rowstride,
02788                                 gint x_align, gint y_align,
02789                                 GdkRgbCmap * cmap)
02790 {
02791    int x, y;
02792    guchar *obuf, *obptr;
02793    gint bpl;
02794    guchar *bptr, *bp2;
02795    gint r, g, b;
02796    gint r_right, r_left, r_prec;
02797    gint g_right, g_left, g_prec;
02798    gint b_right, b_left, b_prec;
02799    gint bpp;
02800    guint32 pixel;
02801    gint shift, shift_init;
02802    gint dith;
02803    gint r1, g1, b1;
02804    const guchar *dmp;
02805 
02806    r_right = 8 - image_info->visual->red_prec;
02807    r_left = image_info->visual->red_shift;
02808    r_prec = image_info->visual->red_prec;
02809    g_right = 8 - image_info->visual->green_prec;
02810    g_left = image_info->visual->green_shift;
02811    g_prec = image_info->visual->green_prec;
02812    b_right = 8 - image_info->visual->blue_prec;
02813    b_left = image_info->visual->blue_shift;
02814    b_prec = image_info->visual->blue_prec;
02815    bpp = image_info->bpp;
02816    bptr = buf;
02817    bpl = image->bpl;
02818    obuf = ((guchar *) image->mem) + y0 * bpl + x0 * bpp;
02819    shift_init = (bpp - 1) << 3;
02820    for (y = 0; y < height; y++) {
02821       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
02822       obptr = obuf;
02823       bp2 = bptr;
02824       for (x = 0; x < width; x++) {
02825          r = bp2[0];
02826          g = bp2[1];
02827          b = bp2[2];
02828          dith = dmp[(x_align + x) & (DM_WIDTH - 1)] << 2;
02829          r1 = r + (dith >> r_prec);
02830          g1 = g + ((252 - dith) >> g_prec);
02831          b1 = b + (dith >> b_prec);
02832          pixel = (((r1 - (r1 >> r_prec)) >> r_right) << r_left) |
02833              (((g1 - (g1 >> g_prec)) >> g_right) << g_left) |
02834              (((b1 - (b1 >> b_prec)) >> b_right) << b_left);
02835          for (shift = shift_init; shift >= 0; shift -= 8) {
02836             *obptr++ = (pixel >> shift) & 0xff;
02837          }
02838          bp2 += 3;
02839       }
02840       bptr += rowstride;
02841       obuf += bpl;
02842    }
02843 }
02844 
02845 /* This actually works for depths from 3 to 7 */
02846 static void
02847 gdk_rgb_convert_4(GdkImage * image,
02848                   gint x0, gint y0, gint width, gint height,
02849                   guchar * buf, int rowstride,
02850                   gint x_align, gint y_align, GdkRgbCmap * cmap)
02851 {
02852    int x, y;
02853    gint bpl;
02854    guchar *obuf, *obptr;
02855    guchar *bptr, *bp2;
02856    gint r, g, b;
02857    const guchar *dmp;
02858    gint dith;
02859 
02860    bptr = buf;
02861    bpl = image->bpl;
02862    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
02863    for (y = 0; y < height; y++) {
02864       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
02865       bp2 = bptr;
02866       obptr = obuf;
02867       for (x = 0; x < width; x += 1) {
02868          r = *bp2++;
02869          g = *bp2++;
02870          b = *bp2++;
02871          dith = (dmp[(x_align + x) & (DM_WIDTH - 1)] << 2) | 3;
02872          obptr[0] = colorcube_d[(((r + dith) & 0x100) >> 2) |
02873                                 (((g + 258 - dith) & 0x100) >> 5) |
02874                                 (((b + dith) & 0x100) >> 8)];
02875          obptr++;
02876       }
02877       bptr += rowstride;
02878       obuf += bpl;
02879    }
02880 }
02881 
02882 /* This actually works for depths from 3 to 7 */
02883 static void
02884 gdk_rgb_convert_gray4(GdkImage * image,
02885                       gint x0, gint y0, gint width, gint height,
02886                       guchar * buf, int rowstride,
02887                       gint x_align, gint y_align, GdkRgbCmap * cmap)
02888 {
02889    int x, y;
02890    gint bpl;
02891    guchar *obuf, *obptr;
02892    guchar *bptr, *bp2;
02893    gint r, g, b;
02894    gint shift;
02895 
02896    bptr = buf;
02897    bpl = image->bpl;
02898    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
02899    shift = 9 - image_info->visual->depth;
02900    for (y = 0; y < height; y++) {
02901       bp2 = bptr;
02902       obptr = obuf;
02903       for (x = 0; x < width; x++) {
02904          r = *bp2++;
02905          g = *bp2++;
02906          b = *bp2++;
02907          obptr[0] = (g + ((b + r) >> 1)) >> shift;
02908          obptr++;
02909       }
02910       bptr += rowstride;
02911       obuf += bpl;
02912    }
02913 }
02914 
02915 static void
02916 gdk_rgb_convert_gray4_pack(GdkImage * image,
02917                            gint x0, gint y0, gint width, gint height,
02918                            guchar * buf, int rowstride,
02919                            gint x_align, gint y_align, GdkRgbCmap * cmap)
02920 {
02921    int x, y;
02922    gint bpl;
02923    guchar *obuf, *obptr;
02924    guchar *bptr, *bp2;
02925    gint r, g, b;
02926    gint shift;
02927    guchar pix0, pix1;
02928    /* todo: this is hardcoded to big-endian. Make endian-agile. */
02929 
02930    bptr = buf;
02931    bpl = image->bpl;
02932    obuf = ((guchar *) image->mem) + y0 * bpl + (x0 >> 1);
02933    shift = 9 - image_info->visual->depth;
02934    for (y = 0; y < height; y++) {
02935       bp2 = bptr;
02936       obptr = obuf;
02937       for (x = 0; x < width; x += 2) {
02938          r = *bp2++;
02939          g = *bp2++;
02940          b = *bp2++;
02941          pix0 = (g + ((b + r) >> 1)) >> shift;
02942          r = *bp2++;
02943          g = *bp2++;
02944          b = *bp2++;
02945          pix1 = (g + ((b + r) >> 1)) >> shift;
02946          obptr[0] = (pix0 << 4) | pix1;
02947          obptr++;
02948       }
02949       if (width & 1) {
02950          r = *bp2++;
02951          g = *bp2++;
02952          b = *bp2++;
02953          pix0 = (g + ((b + r) >> 1)) >> shift;
02954          obptr[0] = (pix0 << 4);
02955       }
02956       bptr += rowstride;
02957       obuf += bpl;
02958    }
02959 }
02960 
02961 /* This actually works for depths from 3 to 7 */
02962 static void
02963 gdk_rgb_convert_gray4_d(GdkImage * image,
02964                         gint x0, gint y0, gint width, gint height,
02965                         guchar * buf, int rowstride,
02966                         gint x_align, gint y_align, GdkRgbCmap * cmap)
02967 {
02968    int x, y;
02969    gint bpl;
02970    guchar *obuf, *obptr;
02971    guchar *bptr, *bp2;
02972    gint r, g, b;
02973    const guchar *dmp;
02974    gint prec, right;
02975    gint gray;
02976 
02977    bptr = buf;
02978    bpl = image->bpl;
02979    obuf = ((guchar *) image->mem) + y0 * bpl + x0;
02980    prec = image_info->visual->depth;
02981    right = 8 - prec;
02982    for (y = 0; y < height; y++) {
02983       bp2 = bptr;
02984       obptr = obuf;
02985       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
02986       for (x = 0; x < width; x++) {
02987          r = *bp2++;
02988          g = *bp2++;
02989          b = *bp2++;
02990          gray = (g + ((b + r) >> 1)) >> 1;
02991          gray += (dmp[(x_align + x) & (DM_WIDTH - 1)] << 2) >> prec;
02992          obptr[0] = (gray - (gray >> prec)) >> right;
02993          obptr++;
02994       }
02995       bptr += rowstride;
02996       obuf += bpl;
02997    }
02998 }
02999 
03000 static void
03001 gdk_rgb_convert_gray4_d_pack(GdkImage * image,
03002                              gint x0, gint y0, gint width, gint height,
03003                              guchar * buf, int rowstride,
03004                              gint x_align, gint y_align, GdkRgbCmap * cmap)
03005 {
03006    int x, y;
03007    gint bpl;
03008    guchar *obuf, *obptr;
03009    guchar *bptr, *bp2;
03010    gint r, g, b;
03011    const guchar *dmp;
03012    gint prec, right;
03013    gint gray;
03014    guchar pix0, pix1;
03015    /* todo: this is hardcoded to big-endian. Make endian-agile. */
03016 
03017    bptr = buf;
03018    bpl = image->bpl;
03019    obuf = ((guchar *) image->mem) + y0 * bpl + (x0 >> 1);
03020    prec = image_info->visual->depth;
03021    right = 8 - prec;
03022    for (y = 0; y < height; y++) {
03023       bp2 = bptr;
03024       obptr = obuf;
03025       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
03026       for (x = 0; x < width; x += 2) {
03027          r = *bp2++;
03028          g = *bp2++;
03029          b = *bp2++;
03030          gray = (g + ((b + r) >> 1)) >> 1;
03031          gray += (dmp[(x_align + x) & (DM_WIDTH - 1)] << 2) >> prec;
03032          pix0 = (gray - (gray >> prec)) >> right;
03033          r = *bp2++;
03034          g = *bp2++;
03035          b = *bp2++;
03036          gray = (g + ((b + r) >> 1)) >> 1;
03037          gray += (dmp[(x_align + x + 1) & (DM_WIDTH - 1)] << 2) >> prec;
03038          pix1 = (gray - (gray >> prec)) >> right;
03039          obptr[0] = (pix0 << 4) | pix1;
03040          obptr++;
03041       }
03042       if (width & 1) {
03043          r = *bp2++;
03044          g = *bp2++;
03045          b = *bp2++;
03046          gray = (g + ((b + r) >> 1)) >> 1;
03047          gray += (dmp[(x_align + x + 1) & (DM_WIDTH - 1)] << 2) >> prec;
03048          pix0 = (gray - (gray >> prec)) >> right;
03049          obptr[0] = (pix0 << 4);
03050       }
03051       bptr += rowstride;
03052       obuf += bpl;
03053    }
03054 }
03055 
03056 static void
03057 gdk_rgb_convert_1(GdkImage * image,
03058                   gint x0, gint y0, gint width, gint height,
03059                   guchar * buf, int rowstride,
03060                   gint x_align, gint y_align, GdkRgbCmap * cmap)
03061 {
03062    int x, y;
03063    gint bpl;
03064    guchar *obuf, *obptr;
03065    guchar *bptr, *bp2;
03066    gint r, g, b;
03067    const guchar *dmp;
03068    gint dith;
03069    guchar byte;
03070 
03071    bptr = buf;
03072    bpl = image->bpl;
03073    obuf = ((guchar *) image->mem) + y0 * bpl + (x0 >> 3);
03074    byte = 0;                    /* unnecessary, but it keeps gcc from complaining */
03075    for (y = 0; y < height; y++) {
03076       dmp = DM[(y_align + y) & (DM_HEIGHT - 1)];
03077       bp2 = bptr;
03078       obptr = obuf;
03079       for (x = 0; x < width; x++) {
03080          r = *bp2++;
03081          g = *bp2++;
03082          b = *bp2++;
03083          dith = (dmp[(x_align + x) & (DM_WIDTH - 1)] << 4) | 4;
03084          byte += byte + (r + g + g + b + dith > 1020);
03085          if ((x & 7) == 7) {
03086             obptr[0] = byte;
03087             obptr++;
03088          }
03089       }
03090       if (x & 7)
03091          obptr[0] = byte << (8 - (x & 7));
03092       bptr += rowstride;
03093       obuf += bpl;
03094    }
03095 }
03096 
03097 /* Returns a pointer to the stage buffer. */
03098 static guchar *gdk_rgb_ensure_stage(void)
03099 {
03100    if (image_info->stage_buf == NULL)
03101       image_info->stage_buf = g_malloc(IMAGE_HEIGHT * STAGE_ROWSTRIDE);
03102    return image_info->stage_buf;
03103 }
03104 
03105 /* This is slow. Speed me up, please. */
03106 static void
03107 gdk_rgb_32_to_stage(guchar * buf, gint rowstride, gint width, gint height)
03108 {
03109    gint x, y;
03110    guchar *pi_start, *po_start;
03111    guchar *pi, *po;
03112 
03113    pi_start = buf;
03114    po_start = gdk_rgb_ensure_stage();
03115    for (y = 0; y < height; y++) {
03116       pi = pi_start;
03117       po = po_start;
03118       for (x = 0; x < width; x++) {
03119          *po++ = *pi++;
03120          *po++ = *pi++;
03121          *po++ = *pi++;
03122          pi++;
03123       }
03124       pi_start += rowstride;
03125       po_start += STAGE_ROWSTRIDE;
03126    }
03127 }
03128 
03129 /* Generic 32bit RGB conversion function - convert to 24bit packed, then
03130    go from there. */
03131 static void
03132 gdk_rgb_convert_32_generic(GdkImage * image,
03133                            gint x0, gint y0, gint width, gint height,
03134                            guchar * buf, gint rowstride,
03135                            gint x_align, gint y_align, GdkRgbCmap * cmap)
03136 {
03137    gdk_rgb_32_to_stage(buf, rowstride, width, height);
03138 
03139    (*image_info->conv) (image, x0, y0, width, height,
03140                         image_info->stage_buf, STAGE_ROWSTRIDE,
03141                         x_align, y_align, cmap);
03142 }
03143 
03144 /* Generic 32bit RGB conversion function - convert to 24bit packed, then
03145    go from there. */
03146 static void
03147 gdk_rgb_convert_32_generic_d(GdkImage * image,
03148                              gint x0, gint y0, gint width, gint height,
03149                              guchar * buf, gint rowstride,
03150                              gint x_align, gint y_align, GdkRgbCmap * cmap)
03151 {
03152    gdk_rgb_32_to_stage(buf, rowstride, width, height);
03153 
03154    (*image_info->conv_d) (image, x0, y0, width, height,
03155                           image_info->stage_buf, STAGE_ROWSTRIDE,
03156                           x_align, y_align, cmap);
03157 }
03158 
03159 /* This is slow. Speed me up, please. */
03160 static void
03161 gdk_rgb_gray_to_stage(guchar * buf, gint rowstride, gint width,
03162                       gint height)
03163 {
03164    gint x, y;
03165    guchar *pi_start, *po_start;
03166    guchar *pi, *po;
03167    guchar gray;
03168 
03169    pi_start = buf;
03170    po_start = gdk_rgb_ensure_stage();
03171    for (y = 0; y < height; y++) {
03172       pi = pi_start;
03173       po = po_start;
03174       for (x = 0; x < width; x++) {
03175          gray = *pi++;
03176          *po++ = gray;
03177          *po++ = gray;
03178          *po++ = gray;
03179       }
03180       pi_start += rowstride;
03181       po_start += STAGE_ROWSTRIDE;
03182    }
03183 }
03184 
03185 /* Generic gray conversion function - convert to 24bit packed, then go
03186    from there. */
03187 static void
03188 gdk_rgb_convert_gray_generic(GdkImage * image,
03189                              gint x0, gint y0, gint width, gint height,
03190                              guchar * buf, gint rowstride,
03191                              gint x_align, gint y_align, GdkRgbCmap * cmap)
03192 {
03193    gdk_rgb_gray_to_stage(buf, rowstride, width, height);
03194 
03195    (*image_info->conv) (image, x0, y0, width, height,
03196                         image_info->stage_buf, STAGE_ROWSTRIDE,
03197                         x_align, y_align, cmap);
03198 }
03199 
03200 static void
03201 gdk_rgb_convert_gray_generic_d(GdkImage * image,
03202                                gint x0, gint y0, gint width, gint height,
03203                                guchar * buf, gint rowstride,
03204                                gint x_align, gint y_align,
03205                                GdkRgbCmap * cmap)
03206 {
03207    gdk_rgb_gray_to_stage(buf, rowstride, width, height);
03208 
03209    (*image_info->conv_d) (image, x0, y0, width, height,
03210                           image_info->stage_buf, STAGE_ROWSTRIDE,
03211                           x_align, y_align, cmap);
03212 }
03213 
03214 /* Render grayscale using indexed method. */
03215 static void
03216 gdk_rgb_convert_gray_cmap(GdkImage * image,
03217                           gint x0, gint y0, gint width, gint height,
03218                           guchar * buf, gint rowstride,
03219                           gint x_align, gint y_align, GdkRgbCmap * cmap)
03220 {
03221    (*image_info->conv_indexed) (image, x0, y0, width, height,
03222                                 buf, rowstride,
03223                                 x_align, y_align, image_info->gray_cmap);
03224 }
03225 
03226 #if 0
03227 static void
03228 gdk_rgb_convert_gray_cmap_d(GdkImage * image,
03229                             gint x0, gint y0, gint width, gint height,
03230                             guchar * buf, gint rowstride,
03231                             gint x_align, gint y_align, GdkRgbCmap * cmap)
03232 {
03233    (*image_info->conv_indexed_d) (image, x0, y0, width, height,
03234                                   buf, rowstride,
03235                                   x_align, y_align, image_info->gray_cmap);
03236 }
03237 #endif
03238 
03239 /* This is slow. Speed me up, please. */
03240 static void
03241 gdk_rgb_indexed_to_stage(guchar * buf, gint rowstride, gint width,
03242                          gint height, GdkRgbCmap * cmap)
03243 {
03244    gint x, y;
03245    guchar *pi_start, *po_start;
03246    guchar *pi, *po;
03247    gint rgb;
03248 
03249    pi_start = buf;
03250    po_start = gdk_rgb_ensure_stage();
03251    for (y = 0; y < height; y++) {
03252       pi = pi_start;
03253       po = po_start;
03254       for (x = 0; x < width; x++) {
03255          rgb = cmap->colors[*pi++];
03256          *po++ = rgb >> 16;
03257          *po++ = (rgb >> 8) & 0xff;
03258          *po++ = rgb & 0xff;
03259       }
03260       pi_start += rowstride;
03261       po_start += STAGE_ROWSTRIDE;
03262    }
03263 }
03264 
03265 /* Generic gray conversion function - convert to 24bit packed, then go
03266    from there. */
03267 static void
03268 gdk_rgb_convert_indexed_generic(GdkImage * image,
03269                                 gint x0, gint y0, gint width, gint height,
03270                                 guchar * buf, gint rowstride,
03271                                 gint x_align, gint y_align,
03272                                 GdkRgbCmap * cmap)
03273 {
03274    gdk_rgb_indexed_to_stage(buf, rowstride, width, height, cmap);
03275 
03276    (*image_info->conv) (image, x0, y0, width, height,
03277                         image_info->stage_buf, STAGE_ROWSTRIDE,
03278                         x_align, y_align, cmap);
03279 }
03280 
03281 static void
03282 gdk_rgb_convert_indexed_generic_d(GdkImage * image,
03283                                   gint x0, gint y0, gint width,
03284                                   gint height, guchar * buf,
03285                                   gint rowstride, gint x_align,
03286                                   gint y_align, GdkRgbCmap * cmap)
03287 {
03288    gdk_rgb_indexed_to_stage(buf, rowstride, width, height, cmap);
03289 
03290    (*image_info->conv_d) (image, x0, y0, width, height,
03291                           image_info->stage_buf, STAGE_ROWSTRIDE,
03292                           x_align, y_align, cmap);
03293 }
03294 
03295 /* Select a conversion function based on the visual and a
03296    representative image. */
03297 static void gdk_rgb_select_conv(GdkImage * image)
03298 {
03299    GdkByteOrder byte_order;
03300    gint depth, bpp, byterev;
03301    GdkVisualType vtype;
03302    guint32 red_mask, green_mask, blue_mask;
03303    GdkRgbConvFunc conv, conv_d;
03304    GdkRgbConvFunc conv_32, conv_32_d;
03305    GdkRgbConvFunc conv_gray, conv_gray_d;
03306    GdkRgbConvFunc conv_indexed, conv_indexed_d;
03307    gboolean mask_rgb, mask_bgr;
03308 
03309    depth = image_info->visual->depth;
03310 
03311    /* FIXME: save the bpp in the image; this is hack that works for
03312     *        common visuals, not otherwise.
03313     */
03314    if (depth <= 8)
03315       bpp = depth;
03316    else
03317       bpp = 8 * image->bpp;
03318 
03319    byte_order = image->byte_order;
03320    if (gdk_rgb_verbose)
03321       g_print("Chose visual type=%s depth=%d, image bpp=%d, %s first\n",
03322               visual_names[image_info->visual->type],
03323               image_info->visual->depth, bpp,
03324               byte_order == GDK_LSB_FIRST ? "lsb" : "msb");
03325 
03326 #if G_BYTE_ORDER == G_BIG_ENDIAN
03327    byterev = (byte_order == GDK_LSB_FIRST);
03328 #else
03329    byterev = (byte_order == GDK_MSB_FIRST);
03330 #endif
03331 
03332    vtype = image_info->visual->type;
03333    if (vtype == GDK_VISUAL_DIRECT_COLOR)
03334       vtype = GDK_VISUAL_TRUE_COLOR;
03335 
03336    red_mask = image_info->visual->red_mask;
03337    green_mask = image_info->visual->green_mask;
03338    blue_mask = image_info->visual->blue_mask;
03339 
03340    mask_rgb = red_mask == 0xff0000 && green_mask == 0xff00
03341        && blue_mask == 0xff;
03342    mask_bgr = red_mask == 0xff && green_mask == 0xff00
03343        && blue_mask == 0xff0000;
03344 
03345    conv = NULL;
03346    conv_d = NULL;
03347 
03348    conv_32 = gdk_rgb_convert_32_generic;
03349    conv_32_d = gdk_rgb_convert_32_generic_d;
03350 
03351    conv_gray = gdk_rgb_convert_gray_generic;
03352    conv_gray_d = gdk_rgb_convert_gray_generic_d;
03353 
03354    conv_indexed = gdk_rgb_convert_indexed_generic;
03355    conv_indexed_d = gdk_rgb_convert_indexed_generic_d;
03356 
03357    image_info->dith_default = FALSE;
03358 
03359    if (image_info->bitmap)
03360       conv = gdk_rgb_convert_1;
03361    else if (bpp == 16 && depth == 16 && !byterev &&
03362             red_mask == 0xf800 && green_mask == 0x7e0 && blue_mask == 0x1f)
03363    {
03364       conv = gdk_rgb_convert_565;
03365       conv_d = gdk_rgb_convert_565_d;
03366       conv_gray = gdk_rgb_convert_565_gray;
03367       gdk_rgb_preprocess_dm_565();
03368    } else if (bpp == 16 && depth == 16 &&
03369               vtype == GDK_VISUAL_TRUE_COLOR && byterev &&
03370               red_mask == 0xf800 && green_mask == 0x7e0
03371               && blue_mask == 0x1f)
03372       conv = gdk_rgb_convert_565_br;
03373 
03374    else if (bpp == 16 && depth == 15 &&
03375             vtype == GDK_VISUAL_TRUE_COLOR && !byterev &&
03376             red_mask == 0x7c00 && green_mask == 0x3e0 && blue_mask == 0x1f)
03377       conv = gdk_rgb_convert_555;
03378 
03379    else if (bpp == 16 && depth == 15 &&
03380             vtype == GDK_VISUAL_TRUE_COLOR && byterev &&
03381             red_mask == 0x7c00 && green_mask == 0x3e0 && blue_mask == 0x1f)
03382       conv = gdk_rgb_convert_555_br;
03383 
03384    /* I'm not 100% sure about the 24bpp tests - but testing will show */
03385    else if (bpp == 24 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03386             ((mask_rgb && byte_order == GDK_LSB_FIRST) ||
03387              (mask_bgr && byte_order == GDK_MSB_FIRST)))
03388       conv = gdk_rgb_convert_888_lsb;
03389    else if (bpp == 24 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03390             ((mask_rgb && byte_order == GDK_MSB_FIRST) ||
03391              (mask_bgr && byte_order == GDK_LSB_FIRST)))
03392       conv = gdk_rgb_convert_888_msb;
03393 #if G_BYTE_ORDER == G_BIG_ENDIAN
03394    else if (bpp == 32 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03395             (mask_rgb && byte_order == GDK_LSB_FIRST))
03396       conv = gdk_rgb_convert_0888_br;
03397    else if (bpp == 32 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03398             (mask_rgb && byte_order == GDK_MSB_FIRST))
03399       conv = gdk_rgb_convert_0888;
03400    else if (bpp == 32 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03401             (mask_bgr && byte_order == GDK_MSB_FIRST))
03402       conv = gdk_rgb_convert_8880_br;
03403 #else
03404    else if (bpp == 32 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03405             (mask_rgb && byte_order == GDK_MSB_FIRST))
03406       conv = gdk_rgb_convert_0888_br;
03407    else if (bpp == 32 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03408             (mask_rgb && byte_order == GDK_LSB_FIRST))
03409       conv = gdk_rgb_convert_0888;
03410    else if (bpp == 32 && depth == 24 && vtype == GDK_VISUAL_TRUE_COLOR &&
03411             (mask_bgr && byte_order == GDK_LSB_FIRST))
03412       conv = gdk_rgb_convert_8880_br;
03413 #endif
03414 
03415    else if (vtype == GDK_VISUAL_TRUE_COLOR && byte_order == GDK_LSB_FIRST) {
03416       conv = gdk_rgb_convert_truecolor_lsb;
03417       conv_d = gdk_rgb_convert_truecolor_lsb_d;
03418    } else if (vtype == GDK_VISUAL_TRUE_COLOR
03419               && byte_order == GDK_MSB_FIRST) {
03420       conv = gdk_rgb_convert_truecolor_msb;
03421       conv_d = gdk_rgb_convert_truecolor_msb_d;
03422    } else if (bpp == 8 && depth == 8 && (vtype == GDK_VISUAL_PSEUDO_COLOR
03423 #ifdef ENABLE_GRAYSCALE
03424                                          || vtype == GDK_VISUAL_GRAYSCALE
03425 #endif
03426               )) {
03427       image_info->dith_default = TRUE;
03428       conv = gdk_rgb_convert_8;
03429       if (vtype != GDK_VISUAL_GRAYSCALE) {
03430          if (image_info->nred_shades == 6 &&
03431              image_info->ngreen_shades == 6 &&
03432              image_info->nblue_shades == 6)
03433             conv_d = gdk_rgb_convert_8_d666;
03434          else
03435             conv_d = gdk_rgb_convert_8_d;
03436       }
03437       conv_indexed = gdk_rgb_convert_8_indexed;
03438       conv_gray = gdk_rgb_convert_gray_cmap;
03439    } else if (bpp == 8 && depth == 8 && (vtype == GDK_VISUAL_STATIC_GRAY
03440 #ifdef not_ENABLE_GRAYSCALE
03441                                          || vtype == GDK_VISUAL_GRAYSCALE
03442 #endif
03443               )) {
03444       conv = gdk_rgb_convert_gray8;
03445       conv_gray = gdk_rgb_convert_gray8_gray;
03446    } else if (bpp == 8 && depth < 8 && depth >= 2 &&
03447               (vtype == GDK_VISUAL_STATIC_GRAY
03448                || vtype == GDK_VISUAL_GRAYSCALE)) {
03449       conv = gdk_rgb_convert_gray4;
03450       conv_d = gdk_rgb_convert_gray4_d;
03451    } else if (bpp == 8 && depth < 8 && depth >= 3) {
03452       conv = gdk_rgb_convert_4;
03453    } else if (bpp == 4 && depth <= 4 && depth >= 2 &&
03454               (vtype == GDK_VISUAL_STATIC_GRAY
03455                || vtype == GDK_VISUAL_GRAYSCALE)) {
03456       conv = gdk_rgb_convert_gray4_pack;
03457       conv_d = gdk_rgb_convert_gray4_d_pack;
03458    }
03459 
03460    if (conv_d == NULL)
03461       conv_d = conv;
03462 
03463    image_info->conv = conv;
03464    image_info->conv_d = conv_d;
03465 
03466    image_info->conv_32 = conv_32;
03467    image_info->conv_32_d = conv_32_d;
03468 
03469    image_info->conv_gray = conv_gray;
03470    image_info->conv_gray_d = conv_gray_d;
03471 
03472    image_info->conv_indexed = conv_indexed;
03473    image_info->conv_indexed_d = conv_indexed_d;
03474 }
03475 
03476 static gint horiz_idx;
03477 static gint horiz_y = IMAGE_HEIGHT;
03478 static gint vert_idx;
03479 static gint vert_x = IMAGE_WIDTH;
03480 static gint tile_idx;
03481 static gint tile_x = IMAGE_WIDTH;
03482 static gint tile_y1 = IMAGE_HEIGHT;
03483 static gint tile_y2 = IMAGE_HEIGHT;
03484 
03485 #ifdef VERBOSE
03486 static gint sincelast;
03487 #endif
03488 
03489 /* Defining NO_FLUSH can cause inconsistent screen updates, but is useful
03490    for performance evaluation. */
03491 
03492 #undef NO_FLUSH
03493 
03494 static gint gdk_rgb_alloc_scratch_image(void)
03495 {
03496    if (static_image_idx == N_IMAGES) {
03497 #ifndef NO_FLUSH
03498       gdk_flush();
03499 #endif
03500 #ifdef VERBOSE
03501       g_print("flush, %d puts since last flush\n", sincelast);
03502       sincelast = 0;
03503 #endif
03504       static_image_idx = 0;
03505       horiz_y = IMAGE_HEIGHT;
03506       vert_x = IMAGE_WIDTH;
03507       tile_x = IMAGE_WIDTH;
03508       tile_y1 = tile_y2 = IMAGE_HEIGHT;
03509    }
03510    return static_image_idx++;
03511 }
03512 
03513 static GdkImage *gdk_rgb_alloc_scratch(gint width, gint height, gint * x0,
03514                                        gint * y0)
03515 {
03516    GdkImage *image;
03517    gint idx;
03518 
03519    if (width >= (IMAGE_WIDTH >> 1)) {
03520       if (height >= (IMAGE_HEIGHT >> 1)) {
03521          idx = gdk_rgb_alloc_scratch_image();
03522          *x0 = 0;
03523          *y0 = 0;
03524       } else {
03525          if (height + horiz_y > IMAGE_HEIGHT) {
03526             horiz_idx = gdk_rgb_alloc_scratch_image();
03527             horiz_y = 0;
03528          }
03529          idx = horiz_idx;
03530          *x0 = 0;
03531          *y0 = horiz_y;
03532          horiz_y += height;
03533       }
03534    } else {
03535       if (height >= (IMAGE_HEIGHT >> 1)) {
03536          if (width + vert_x > IMAGE_WIDTH) {
03537             vert_idx = gdk_rgb_alloc_scratch_image();
03538             vert_x = 0;
03539          }
03540          idx = vert_idx;
03541          *x0 = vert_x;
03542          *y0 = 0;
03543          /* using 3 and -4 would be slightly more efficient on 32-bit machines
03544             with > 1bpp displays */
03545          vert_x += (width + 7) & -8;
03546       } else {
03547          if (width + tile_x > IMAGE_WIDTH) {
03548             tile_y1 = tile_y2;
03549             tile_x = 0;
03550          }
03551          if (height + tile_y1 > IMAGE_HEIGHT) {
03552             tile_idx = gdk_rgb_alloc_scratch_image();
03553             tile_x = 0;
03554             tile_y1 = 0;
03555             tile_y2 = 0;
03556          }
03557          if (height + tile_y1 > tile_y2)
03558             tile_y2 = height + tile_y1;
03559          idx = tile_idx;
03560          *x0 = tile_x;
03561          *y0 = tile_y1;
03562          tile_x += (width + 7) & -8;
03563       }
03564    }
03565    image = static_image[idx];
03566 #ifdef VERBOSE
03567    g_print("index %d, x %d, y %d (%d x %d)\n", idx, *x0, *y0, width,
03568            height);
03569    sincelast++;
03570 #endif
03571    return image;
03572 }
03573 
03574 static void
03575 gdk_draw_rgb_image_core(GdkDrawable * drawable,
03576                         GdkGC * gc,
03577                         gint x,
03578                         gint y,
03579                         gint width,
03580                         gint height,
03581                         guchar * buf,
03582                         gint pixstride,
03583                         gint rowstride,
03584                         GdkRgbConvFunc conv,
03585                         GdkRgbCmap * cmap, gint xdith, gint ydith)
03586 {
03587    gint y0, x0;
03588    gint xs0, ys0;
03589    GdkImage *image;
03590    gint width1, height1;
03591    guchar *buf_ptr;
03592 
03593    if (image_info->bitmap) {
03594       if (image_info->own_gc == NULL) {
03595          GdkColor color;
03596 
03597          image_info->own_gc = gdk_gc_new(drawable);
03598          gdk_color_white(image_info->cmap, &color);
03599          gdk_gc_set_foreground(image_info->own_gc, &color);
03600          gdk_color_black(image_info->cmap, &color);
03601          gdk_gc_set_background(image_info->own_gc, &color);
03602       }
03603       gc = image_info->own_gc;
03604    }
03605    for (y0 = 0; y0 < height; y0 += IMAGE_HEIGHT) {
03606       height1 = MIN(height - y0, IMAGE_HEIGHT);
03607       for (x0 = 0; x0 < width; x0 += IMAGE_WIDTH) {
03608          width1 = MIN(width - x0, IMAGE_WIDTH);
03609          buf_ptr = buf + y0 * rowstride + x0 * pixstride;
03610 
03611          image = gdk_rgb_alloc_scratch(width1, height1, &xs0, &ys0);
03612 
03613          conv(image, xs0, ys0, width1, height1, buf_ptr, rowstride,
03614               x + x0 + xdith, y + y0 + ydith, cmap);
03615 
03616 #ifndef DONT_ACTUALLY_DRAW
03617          gdk_draw_image(drawable, gc,
03618                         image, xs0, ys0, x + x0, y + y0, width1, height1);
03619 #endif
03620       }
03621    }
03622 }
03623 
03624 
03625 void
03626 gdk_draw_rgb_image(GdkDrawable * drawable,
03627                    GdkGC * gc,
03628                    gint x,
03629                    gint y,
03630                    gint width,
03631                    gint height,
03632                    GdkRgbDither dith, guchar * rgb_buf, gint rowstride)
03633 {
03634    if (dith == GDK_RGB_DITHER_NONE || (dith == GDK_RGB_DITHER_NORMAL &&
03635                                        !image_info->dith_default))
03636       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03637                               rgb_buf, 3, rowstride, image_info->conv,
03638                               NULL, 0, 0);
03639    else
03640       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03641                               rgb_buf, 3, rowstride, image_info->conv_d,
03642                               NULL, 0, 0);
03643 }
03644 
03645 void
03646 gdk_draw_rgb_image_dithalign(GdkDrawable * drawable,
03647                              GdkGC * gc,
03648                              gint x,
03649                              gint y,
03650                              gint width,
03651                              gint height,
03652                              GdkRgbDither dith,
03653                              guchar * rgb_buf,
03654                              gint rowstride, gint xdith, gint ydith)
03655 {
03656    if (dith == GDK_RGB_DITHER_NONE || (dith == GDK_RGB_DITHER_NORMAL &&
03657                                        !image_info->dith_default))
03658       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03659                               rgb_buf, 3, rowstride, image_info->conv,
03660                               NULL, xdith, ydith);
03661    else
03662       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03663                               rgb_buf, 3, rowstride, image_info->conv_d,
03664                               NULL, xdith, ydith);
03665 }
03666 
03667 void
03668 gdk_draw_rgb_32_image(GdkDrawable * drawable,
03669                       GdkGC * gc,
03670                       gint x,
03671                       gint y,
03672                       gint width,
03673                       gint height,
03674                       GdkRgbDither dith, guchar * buf, gint rowstride)
03675 {
03676    if (dith == GDK_RGB_DITHER_NONE || (dith == GDK_RGB_DITHER_NORMAL &&
03677                                        !image_info->dith_default))
03678       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03679                               buf, 4, rowstride,
03680                               image_info->conv_32, NULL, 0, 0);
03681    else
03682       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03683                               buf, 4, rowstride,
03684                               image_info->conv_32_d, NULL, 0, 0);
03685 }
03686 
03687 static void gdk_rgb_make_gray_cmap(GdkRgbInfo * info)
03688 {
03689    guint32 rgb[256];
03690    gint i;
03691 
03692    for (i = 0; i < 256; i++)
03693       rgb[i] = (i << 16) | (i << 8) | i;
03694    info->gray_cmap = gdk_rgb_cmap_new(rgb, 256);
03695 }
03696 
03697 void
03698 gdk_draw_gray_image(GdkDrawable * drawable,
03699                     GdkGC * gc,
03700                     gint x,
03701                     gint y,
03702                     gint width,
03703                     gint height,
03704                     GdkRgbDither dith, guchar * buf, gint rowstride)
03705 {
03706    if (image_info->bpp == 1 &&
03707        image_info->gray_cmap == NULL &&
03708        (image_info->visual->type == GDK_VISUAL_PSEUDO_COLOR ||
03709         image_info->visual->type == GDK_VISUAL_GRAYSCALE))
03710       gdk_rgb_make_gray_cmap(image_info);
03711 
03712    if (dith == GDK_RGB_DITHER_NONE || (dith == GDK_RGB_DITHER_NORMAL &&
03713                                        !image_info->dith_default))
03714       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03715                               buf, 1, rowstride,
03716                               image_info->conv_gray, NULL, 0, 0);
03717    else
03718       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03719                               buf, 1, rowstride,
03720                               image_info->conv_gray_d, NULL, 0, 0);
03721 }
03722 
03723 GdkRgbCmap *gdk_rgb_cmap_new(guint32 * colors, gint n_colors)
03724 {
03725    GdkRgbCmap *cmap;
03726    int i, j;
03727    guint32 rgb;
03728 
03729    g_return_val_if_fail(n_colors >= 0, NULL);
03730    g_return_val_if_fail(n_colors <= 256, NULL);
03731    cmap = g_new(GdkRgbCmap, 1);
03732    memcpy(cmap->colors, colors, n_colors * sizeof(guint32));
03733    if (image_info->bpp == 1 &&
03734        (image_info->visual->type == GDK_VISUAL_PSEUDO_COLOR ||
03735         image_info->visual->type == GDK_VISUAL_GRAYSCALE))
03736       for (i = 0; i < n_colors; i++) {
03737          rgb = colors[i];
03738          j = ((rgb & 0xf00000) >> 12) |
03739              ((rgb & 0xf000) >> 8) | ((rgb & 0xf0) >> 4);
03740 #ifdef VERBOSE
03741          g_print("%d %x %x %d\n", i, j, colorcube[j]);
03742 #endif
03743          cmap->lut[i] = colorcube[j];
03744       }
03745    return cmap;
03746 }
03747 
03748 void gdk_rgb_cmap_free(GdkRgbCmap * cmap)
03749 {
03750    g_free(cmap);
03751 }
03752 
03753 void
03754 gdk_draw_indexed_image(GdkDrawable * drawable,
03755                        GdkGC * gc,
03756                        gint x,
03757                        gint y,
03758                        gint width,
03759                        gint height,
03760                        GdkRgbDither dith,
03761                        guchar * buf, gint rowstride, GdkRgbCmap * cmap)
03762 {
03763    if (dith == GDK_RGB_DITHER_NONE || (dith == GDK_RGB_DITHER_NORMAL &&
03764                                        !image_info->dith_default))
03765       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03766                               buf, 1, rowstride,
03767                               image_info->conv_indexed, cmap, 0, 0);
03768    else
03769       gdk_draw_rgb_image_core(drawable, gc, x, y, width, height,
03770                               buf, 1, rowstride,
03771                               image_info->conv_indexed_d, cmap, 0, 0);
03772 }
03773 
03774 gboolean gdk_rgb_ditherable(void)
03775 {
03776    return (image_info->conv != image_info->conv_d);
03777 }
03778 
03779 GdkColormap *gdk_rgb_get_cmap(void)
03780 {
03781    gdk_rgb_init();
03782    return image_info->cmap;
03783 }
03784 
03785 GdkVisual *gdk_rgb_get_visual(void)
03786 {
03787    gdk_rgb_init();
03788    return image_info->visual;
03789 }

Generated on Tue Jul 5 14:14:38 2011 for ROOT_528-00b_version by  doxygen 1.5.1