diff --git a/lib/modules/_Image_PSD.pmod b/lib/modules/_Image_PSD.pmod
index 431ed1519d3744d4de06370d14f9e4c68f84f3db..5851238059919ca4a2a35c5d787d55e6becc013e 100644
--- a/lib/modules/_Image_PSD.pmod
+++ b/lib/modules/_Image_PSD.pmod
@@ -4,7 +4,7 @@ inherit Image._PSD;
 
 class Layer
 {
-  string mode;
+  string mode, name;
   int opacity;
   object image;
   object alpha;
@@ -16,43 +16,12 @@ class Layer
   int mask_flags;
   int mask_xoffset, mask_yoffset;
   int mask_width, mask_height;
-
-
-  Layer copy()
-  {
-    Layer l = Layer();
-    l->mode = mode;
-    l->opacity = opacity;
-    l->image = image;
-    l->alpha = alpha;
-    l->flags = flags;
-    l->xoffset = xoffset;
-    l->yoffset = yoffset;
-    l->width = width;
-    l->height = height;
-    return l;
-  }
-
-
-  Layer get_opaqued( int opaque_value )
-  {
-    Layer res = copy();
-    if(opaque_value != 255)
-    {
-      if(res->alpha)
-        res->alpha *= opaque_value/255.0;
-      else
-        res->alpha = Image.image(width,height,
-                                 opaque_value,opaque_value,opaque_value);
-    }
-    return res;
-  }
 }
 
 int foo;
 Layer decode_layer(mapping layer, mapping i)
 {
-//   int stt = gethrtime();
+  int stt = gethrtime();
   Layer l = Layer();
   int use_cmap;
   l->opacity = layer->opacity;
@@ -63,6 +32,7 @@ Layer decode_layer(mapping layer, mapping i)
   l->image = Image.image( l->width, l->height );
   l->mode = layer->mode;
   l->flags = layer->flags;
+  l->name = layer->name;
 
   l->mask_width = layer->mask_right-layer->mask_left;
   l->mask_height = layer->mask_bottom-layer->mask_top;
@@ -98,10 +68,11 @@ Layer decode_layer(mapping layer, mapping i)
        }
        if( mode )
        {
-//          int st = gethrtime();
+         int st = gethrtime();
          if( !sizeof(lays) )
            lays += ({ 
-             Image.Layer(___decode_image_channel(l->width, l->height,
+             Image.Layer(___decode_image_channel(l->width,
+						 l->height,
                                                  c->data))
            });
          else
@@ -111,16 +82,15 @@ Layer decode_layer(mapping layer, mapping i)
              "mode":mode, 
 	   ]) )
            }));
-//          werror(mode+" took %4.5f seconds\n", (gethrtime()-st)/1000000.0 );
+         werror(mode+" took %4.5f seconds\n", (gethrtime()-st)/1000000.0 );
          c->data = 0;
        }
      }
-//      int st = gethrtime();
+     int st = gethrtime();
      l->image = Image.lay( lays )->image();
-//      werror("combine took %4.5f seconds\n", (gethrtime()-st)/1000000.0 );
+     werror("combine took %4.5f seconds\n", (gethrtime()-st)/1000000.0 );
      break;
-
-   case CMYK:
+    case CMYK:
      inverted = 1;
      colors = ({ ({255,0,0,}),
                  ({0,255,0,}),
@@ -140,7 +110,7 @@ Layer decode_layer(mapping layer, mapping i)
      })*24;
      break;
   }
-//   int st = gethrtime();
+  int st = gethrtime();
   foreach(layer->channels, mapping c)
   {
     object tmp;
@@ -193,8 +163,8 @@ Layer decode_layer(mapping layer, mapping i)
     }
     c->data = 0;
   }
-//   werror("alpha/mask took %4.5f seconds\n", (gethrtime()-st)/1000000.0 );
-//   werror("TOTAL took %4.5f seconds\n\n", (gethrtime()-stt)/1000000.0 );
+  werror("alpha/mask took %4.5f seconds\n", (gethrtime()-st)/1000000.0 );
+  werror("TOTAL took %4.5f seconds\n\n", (gethrtime()-stt)/1000000.0 );
   return l;
 }
 
@@ -306,14 +276,21 @@ array decode_layers( string|mapping what, mapping|void opts )
 
   foreach(reverse(what->layers), object l)
   {
-    if( string m = translate_mode( l->mode ) )
+    if( !(l->flags & LAYER_FLAG_INVISIBLE) || opts->draw_all_layers )
     {
-      Image.Layer lay = Image.Layer( l->image, l->alpha, m );
-      l->image = 0; l->alpha = 0;
-      if( l->opacity != 255 )
-	lay->set_alpha_value( 1.0 - l->opacity / 255.0 );
-      lay->set_offset( l->xoffset, l->yoffset );
-      layers += ({ lay });
+      if( string m = translate_mode( l->mode ) )
+      {
+	Image.Layer lay = Image.Layer( l->image, l->alpha, m );
+
+        lay->set_misc_value( "visible", !(l->flags & LAYER_FLAG_INVISIBLE) );
+        lay->set_misc_value( "name",      l->name );
+
+	l->image = 0; l->alpha = 0;
+	if( l->opacity != 255 )
+	  lay->set_alpha_value( 1.0 - l->opacity / 255.0 );
+	lay->set_offset( l->xoffset, l->yoffset );
+	layers += ({ lay });
+      }
     }
   }
   return layers;
diff --git a/lib/modules/_Image_XCF.pmod b/lib/modules/_Image_XCF.pmod
index a488d92da98fc2698da709e7c9582637bf3374bb..48fe3551c33a2b484a59b691e33feb7178327d47 100644
--- a/lib/modules/_Image_XCF.pmod
+++ b/lib/modules/_Image_XCF.pmod
@@ -424,7 +424,7 @@ array decode_layers( string|object|mapping what, mapping|void opts,
   }
 
   foreach(what->layers, object l)
-    if((l->flags->visible || opts->draw_all_layers) && l->opacity > 0)
+    if((l->flags->visible && l->opacity > 0) || opts->draw_all_layers)
     {
       Image.Layer lay = l->image->get_layer( shrink );
       lay->set_mode( translate_mode( l->mode ) );
diff --git a/src/modules/Image/encodings/psd.c b/src/modules/Image/encodings/psd.c
index 010057c0236456db38bb09151f2e317b03e5c449..a21ee5a6563479754581f69d24398e6e57bc4d5e 100644
--- a/src/modules/Image/encodings/psd.c
+++ b/src/modules/Image/encodings/psd.c
@@ -1,5 +1,5 @@
 #include "global.h"
-RCSID("$Id: psd.c,v 1.22 2000/08/11 18:36:44 grubba Exp $");
+RCSID("$Id: psd.c,v 1.23 2000/11/16 18:26:20 per Exp $");
 
 #include "image_machine.h"
 
@@ -139,6 +139,16 @@ static struct buffer read_string( struct buffer *data )
   return res;
 }
 
+static struct buffer read_pstring( struct buffer *data )
+{
+  struct buffer res;
+  res.len = read_uchar( data );
+  res.str = (unsigned char *)read_data( data, res.len );
+  if(!res.str)
+    error("String read failed\n");
+  return res;
+}
+
 enum image_mode
 {
   Bitmap = 0,
@@ -199,6 +209,7 @@ struct layer
   struct channel_info channel_info[24];
   struct buffer mode;
   struct buffer extra_data;
+  struct buffer name;
 };
 
 static void decode_layers_and_masks( struct psd_image *dst, 
@@ -249,6 +260,7 @@ static void decode_layers_and_masks( struct psd_image *dst,
     layer->flags = read_uchar( src );
     read_uchar( src );
     layer->extra_data = read_string( src );
+    layer->extra_data.len++;
     if(layer->extra_data.len)
     {
       struct buffer tmp = layer->extra_data;
@@ -261,8 +273,14 @@ static void decode_layers_and_masks( struct psd_image *dst,
         layer->mask_bottom = psd_read_int( &tmp2 );
         layer->mask_right  = psd_read_int( &tmp2 );
         layer->mask_default_color = read_uchar( &tmp2 );
-        layer->mask_flags = read_uchar( &tmp2 );
+/*         layer->mask_flags = read_uchar( &tmp2 ); */
+      }
+      tmp2 = read_string( &tmp );
+      if( tmp2.len )
+      {
+	/* ranges (?) */
       }
+      layer->name = read_pstring( &tmp );
     }
   }
   while(layer->next)
@@ -551,6 +569,7 @@ void push_layer( struct layer  *l)
   ref_push_string( s_compression );   push_int( l->compression );
   ref_push_string( s_mode );          push_buffer( &l->mode );
   ref_push_string( s_extra_data );    push_buffer( &l->extra_data );
+  ref_push_string( s_name );          push_buffer( &l->name );
   ref_push_string( s_channels );
   for( i = 0; i<l->num_channels; i++ )
   {
@@ -666,8 +685,8 @@ void init_image_psd()
 
 
 
-  add_integer_constant("LAYER_FLAG_VISIBLE", 0x01, 0 );
-  add_integer_constant("LAYER_FLAG_OBSOLETE", 0x02, 0 );
+  add_integer_constant("LAYER_FLAG_PRESERVE_TRANSPARENCY", 0x01, 0 );
+  add_integer_constant("LAYER_FLAG_INVISIBLE", 0x02, 0 );
   add_integer_constant("LAYER_FLAG_BIT4", 0x04, 0 );
   add_integer_constant("LAYER_FLAG_NOPIX", 0x08, 0 );
 
diff --git a/src/modules/Image/encodings/psd_constant_strings.h b/src/modules/Image/encodings/psd_constant_strings.h
index 75a8959b2a56af884a2b6d4390573e99ec6c0703..1338159edf4ee4be75b4983fc94fd366209b20a8 100644
--- a/src/modules/Image/encodings/psd_constant_strings.h
+++ b/src/modules/Image/encodings/psd_constant_strings.h
@@ -21,6 +21,7 @@ STRING(id);
 STRING(color_data);
 STRING(resource_data);
 STRING(channels);
+STRING(name);
 STRING(data);
 STRING(image_data);
 STRING(layers);