diff --git a/.gitattributes b/.gitattributes
index f9bde4f0ed5f27a06ad186348abe647d00ae1172..b261f01e53139ebc697231104b50983fb1bb424f 100644
--- a/.gitattributes
+++ b/.gitattributes
@@ -136,7 +136,6 @@ testfont binary
 /lib/modules/Parser.pmod/XML.pmod/Tree.pmod foreign_ident
 /lib/modules/Parser.pmod/XML.pmod/testsuite.in foreign_ident
 /lib/modules/Parser.pmod/module.pmod foreign_ident
-/lib/modules/Pike.pmod foreign_ident
 /lib/modules/Protocols.pmod/DNS.pmod foreign_ident
 /lib/modules/Protocols.pmod/HTTP.pmod/Query.pike foreign_ident
 /lib/modules/Protocols.pmod/HTTP.pmod/Session.pike foreign_ident
@@ -269,7 +268,6 @@ testfont binary
 /src/block_alloc.h foreign_ident
 /src/block_alloc_h.h foreign_ident
 /src/build_modlist_h foreign_ident
-/src/builtin.cmod foreign_ident
 /src/builtin_functions.c foreign_ident
 /src/builtin_functions.h foreign_ident
 /src/callback.c foreign_ident
diff --git a/lib/modules/Pike.pmod b/lib/modules/Pike.pmod
index 503a866742621b555d39c9343275d71cba5f3c49..f7454e5a2a2cb4cc9653d8f39386df930b2ba2a6 100644
--- a/lib/modules/Pike.pmod
+++ b/lib/modules/Pike.pmod
@@ -3,7 +3,7 @@
 
 // Pike core things that don't belong anywhere else.
 //
-// $Id: Pike.pmod,v 1.8 2003/04/27 02:20:40 nilsson Exp $
+// $Id$
 
 constant WEAK_INDICES = __builtin.PIKE_WEAK_INDICES;
 constant WEAK_VALUES = __builtin.PIKE_WEAK_VALUES;
@@ -13,6 +13,8 @@ constant WEAK = WEAK_INDICES|WEAK_VALUES;
 
 constant BacktraceFrame = __builtin.backtrace_frame;
 
+constant FakeObject = __builtin.FakeObject;
+
 #if constant(__builtin.security)
 // This only exists if the run-time has been compiled with
 // --with-security.
diff --git a/src/builtin.cmod b/src/builtin.cmod
index 7742b31a6be779c50347607c4d8c070fb1e834a2..a07e44bea1642b257593b4ee241c04fcb3235423 100644
--- a/src/builtin.cmod
+++ b/src/builtin.cmod
@@ -2,7 +2,7 @@
 || This file is part of Pike. For copyright information see COPYRIGHT.
 || Pike is distributed under GPL, LGPL and MPL. See the file COPYING
 || for more information.
-|| $Id: builtin.cmod,v 1.134 2003/04/28 00:32:42 mast Exp $
+|| $Id$
 */
 
 #include "global.h"
@@ -1113,6 +1113,54 @@ PIKEFUN array random(mapping m)
 /*! @module Pike
  */
 
+/*! @class FakeObject
+ *!
+ *! Used as a place holder in eg backtraces for objects that
+ *! are unsuitable to have references to in backtraces.
+ *!
+ *! Examples of such objects are instances of @[Thread.MutexKey],
+ *! and @[Nettle.Cipher.State].
+ *!
+ *! @seealso
+ *!   @[backtrace()]
+ */
+PIKECLASS FakeObject
+  program_flags PROGRAM_CONSTANT;
+{
+  PIKEVAR program prog flags ID_PRIVATE|ID_PROTECTED|ID_HIDDEN;
+
+  PIKEFUN void create(program|function|void prog)
+    flags ID_PROTECTED;
+  {
+    struct program *p = prog ? program_from_svalue(prog):NULL;
+    do_free_program(THIS->prog);
+    THIS->prog = p;
+    if (p) add_ref(p);
+  }
+
+  PIKEFUN string _sprintf(int c, mapping|void ignored)
+    flags ID_PROTECTED;
+  {
+    push_text("%O()");
+    if (THIS->prog) {
+      ref_push_program(THIS->prog);
+    } else {
+      ref_push_program(Pike_fp->current_program);
+    }
+    f_sprintf(2);
+  }
+}
+
+/*! @endclass
+ */
+
+static struct object *clone_fake_object(struct program *p)
+{
+  if (p) ref_push_program(p);
+  else push_undefined();
+  return clone_object(FakeObject_program, 1);
+}
+
 /*! @class BacktraceFrame
  */
 
@@ -1500,6 +1548,25 @@ void low_backtrace(struct Pike_interpreter *i)
 				   f->locals[numargs].u.array->item,
 				   varargs, BIT_MIXED);
 	}
+	if (bf->args->type_field & BIT_OBJECT) {
+	  ptrdiff_t i;
+	  for (i = 0; i < bf->args->size; i++) {
+	    struct svalue *s = ITEM(bf->args) + i;
+	    if ((TYPEOF(*s) == T_OBJECT) &&
+		s->u.object->prog &&
+		(s->u.object->prog->flags &
+		 (PROGRAM_DESTRUCT_IMMEDIATE|PROGRAM_CLEAR_STORAGE))) {
+	      /* It is typically a bad idea to have extra references
+	       * to objects with these flags. The flags are usually
+	       * used by stuff like mutex keys and encryption keys
+	       * respectively.
+	       */
+	      struct object *o = clone_fake_object(s->u.object->prog);
+	      free_object(s->u.object);
+	      SET_SVAL(*s, T_OBJECT, 0, object, o);
+	    }
+	  }
+	}
       }
     }
   }