Bug#642750: [PATCH] epiphany-browser: *HIGHLY* unstable on ia64 (IA-64/IPF/Itanium) platform
Émeric Maschino
emeric.maschino at gmail.com
Mon Dec 3 21:24:28 UTC 2012
Thanks Stephan for your hard work.
I just tested Epiphany with the updated packages that you provided in
[1]. Are they self-contained or is yet another updated package
missing?
Indeed, even with your updated packages, Epiphany still crashes with
the scenario I described in this bug report, albeit you don't have to
click again on Debian URL to make it crash. Simply going back to the
Google results page and waiting a little bit is sufficient to trigger
the crash.
And unfortunately, trying to get an informative stacktrace in gdb, I'm
now hitting the SIGTRAP issue [2] :-(
Émeric
[1] http://www.fs-driver.org/debian-ia64/webkitgtk-debs.tar
[1] http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=691576
2012/12/2 Stephan Schreiber <info at fs-driver.org>:
> severity 642750 grave
> tags 642750 + patch
> block 582774 by 642750
> thanks
>
>
>
> While working on this bug I realized that webkit has yet another bug that
> prevents it from working on ia64. I filed the separate bug#694971 for that.
>
> I built the libwebkitgtk-3.0-0 package which was configured with
> --enable-debug. (Wasn't possible with the initial 4GB of memory at all.
> After a memory upgrade to 16GB it took eleven-and-a-half hour on my box with
> the -j2 option.)
>
> Just starting epiphany-browser showed a first hint what is going on:
> ASSERTION FAILED: isCell()
> ../Source/JavaScriptCore/runtime/JSValueInlineMethods.h(491) : JSC::JSCell*
> JSC::JSValue::asCell() const
>
> Webkit uses a variant data type JSValue, which it uses for anything that can
> be a thing on Java script. It can contain an integer number, a float number
> or a pointer to an object - this is 'cell'.
>
> It turned out that the 'isCell()' assertion failed for a JSValue that just
> has been initialized as a pointer.
>
> The arch determines how the JSValue is defined; there are two options (yet),
> one for any 32-bits arch, the other one for 64-bits archs.
>
> You can see this in Source/JavaScriptCore/runtime/JSValue.h - JSValue
> defines an embedded data type 'EncodedValueDescriptor' for that:
>
> #if USE(JSVALUE32_64)
> typedef int64_t EncodedJSValue;
> #else
> typedef void* EncodedJSValue;
> #endif
>
> union EncodedValueDescriptor {
> int64_t asInt64;
> #if USE(JSVALUE32_64)
> double asDouble;
> #elif USE(JSVALUE64)
> JSCell* ptr;
> #endif
>
> #if CPU(BIG_ENDIAN)
> struct {
> int32_t tag;
> int32_t payload;
> } asBits;
> #else
> struct {
> int32_t payload;
> int32_t tag;
> } asBits;
> #endif
> };
>
> ....
>
> #if USE(JSVALUE32_64)
> /*
> * On 32-bit platforms USE(JSVALUE32_64) should be defined, and we
> use a NaN-encoded
> * form for immediates.
> *
> * The encoding makes use of unused NaN space in the IEEE754
> representation. Any value
> * with the top 13 bits set represents a QNaN (with the sign bit
> set). QNaN values
> * can encode a 51-bit payload. Hardware produced and C-library
> payloads typically
> * have a payload of zero. We assume that non-zero payloads are
> available to encode
> * pointer and integer values. Since any 64-bit bit pattern where
> the top 15 bits are
> * all set represents a NaN with a non-zero payload, we can use this
> space in the NaN
> * ranges to encode other values (however there are also other
> ranges of NaN space that
> * could have been selected).
> *
> * For JSValues that do not contain a double value, the high 32 bits
> contain the tag
> * values listed in the enums below, which all correspond to
> NaN-space. In the case of
> * cell, integer and bool values the lower 32 bits (the 'payload')
> contain the pointer
> * integer or boolean value; in the case of all other tags the
> payload is 0.
> */
> enum { Int32Tag = 0xffffffff };
> enum { BooleanTag = 0xfffffffe };
> enum { NullTag = 0xfffffffd };
> enum { UndefinedTag = 0xfffffffc };
> enum { CellTag = 0xfffffffb };
> enum { EmptyValueTag = 0xfffffffa };
> enum { DeletedValueTag = 0xfffffff9 };
>
> enum { LowestTag = DeletedValueTag };
>
> uint32_t tag() const;
> int32_t payload() const;
> #elif USE(JSVALUE64)
> /*
> * On 64-bit platforms USE(JSVALUE64) should be defined, and we use
> a NaN-encoded
> * form for immediates.
> *
> * The encoding makes use of unused NaN space in the IEEE754
> representation. Any value
> * with the top 13 bits set represents a QNaN (with the sign bit
> set). QNaN values
> * can encode a 51-bit payload. Hardware produced and C-library
> payloads typically
> * have a payload of zero. We assume that non-zero payloads are
> available to encode
> * pointer and integer values. Since any 64-bit bit pattern where
> the top 15 bits are
> * all set represents a NaN with a non-zero payload, we can use this
> space in the NaN
> * ranges to encode other values (however there are also other
> ranges of NaN space that
> * could have been selected).
> *
> * This range of NaN space is represented by 64-bit numbers begining
> with the 16-bit
> * hex patterns 0xFFFE and 0xFFFF - we rely on the fact that no
> valid double-precision
> * numbers will begin fall in these ranges.
> *
> * The top 16-bits denote the type of the encoded JSValue:
> *
> * Pointer { 0000:PPPP:PPPP:PPPP
> * / 0001:****:****:****
> * Double { ...
> * \ FFFE:****:****:****
> * Integer { FFFF:0000:IIII:IIII
> *
> * The scheme we have implemented encodes double precision values by
> performing a
> * 64-bit integer addition of the value 2^48 to the number. After
> this manipulation
> * no encoded double-precision value will begin with the pattern
> 0x0000 or 0xFFFF.
> * Values must be decoded by reversing this operation before
> subsequent floating point
> * operations my be peformed.
> *
> * 32-bit signed integers are marked with the 16-bit tag 0xFFFF.
> *
> * The tag 0x0000 denotes a pointer, or another form of tagged
> immediate. Boolean,
> * null and undefined values are represented by specific, invalid
> pointer values:
> *
> * False: 0x06
> * True: 0x07
> * Undefined: 0x0a
> * Null: 0x02
> *
> * These values have the following properties:
> * - Bit 1 (TagBitTypeOther) is set for all four values, allowing
> real pointers to be
> * quickly distinguished from all immediate values, including
> these invalid pointers.
> * - With bit 3 is masked out (TagBitUndefined) Undefined and Null
> share the
> * same value, allowing null & undefined to be quickly detected.
> *
> * No valid JSValue will have the bit pattern 0x0, this is used to
> represent array
> * holes, and as a C++ 'no value' result (e.g. JSValue() has an
> internal value of 0).
> */
>
> // These values are #defines since using static const integers here
> is a ~1% regression!
>
> // This value is 2^48, used to encode doubles such that the encoded
> value will begin
> // with a 16-bit pattern within the range 0x0001..0xFFFE.
> #define DoubleEncodeOffset 0x1000000000000ll
> // If all bits in the mask are set, this indicates an integer
> number,
> // if any but not all are set this value is a double precision
> number.
> #define TagTypeNumber 0xffff000000000000ll
>
> // All non-numeric (bool, null, undefined) immediates have bit 2
> set.
> #define TagBitTypeOther 0x2ll
> #define TagBitBool 0x4ll
> #define TagBitUndefined 0x8ll
> // Combined integer value for non-numeric immediates.
> #define ValueFalse (TagBitTypeOther | TagBitBool | false)
> #define ValueTrue (TagBitTypeOther | TagBitBool | true)
> #define ValueUndefined (TagBitTypeOther | TagBitUndefined)
> #define ValueNull (TagBitTypeOther)
>
> // TagMask is used to check for all types of immediate values
> (either number or 'other').
> #define TagMask (TagTypeNumber | TagBitTypeOther)
>
> // These special values are never visible to JavaScript code; Empty
> is used to represent
> // Array holes, and for uninitialized JSValues. Deleted is used in
> hash table code.
> // These values would map to cell types in the JSValue encoding, but
> not valid GC cell
> // pointer should have either of these values (Empty is null,
> deleted is at an invalid
> // alignment for a GC cell, and in the zero page).
> #define ValueEmpty 0x0ll
> #define ValueDeleted 0x4ll
> #endif
>
>
>
>
>
>
> USE(JSVALUE64) is true on ia64; USE(JSVALUE32_64) is false.
>
> The code on a true USE(JSVALUE64) uses some sophisticated tricks in order to
> get everything in a 64-bits wide data type.
> If you read the comment of the webkit source, you realize that this works as
> long the high 16-bits of the addresses of any allocated memory are cleared.
> But when you look at the crash dumps above, you see a lot of addresses which
> have some upper bits set.
> This is the reason why decoding of the variant data type fails - the
> mentioned failed assertion.
>
> (If you think you have a Déją vu, it is because the Mozilla Java script
> engine uses a similar trick on 64-bit archs, and has a similar problem on
> ia64, for example, see the archived bug#659186.)
>
>
>
> The proposed patch defines a third option
> USE(JSVALUE64W)
> which we use *only* on ia64.
> It uses an encapsulated union without any trick for the variant data type.
> This is portable but
> - the data type is 128-bits wide,
> - Enabling JIT compiler isn't possible - that's not that bad; ia64 doesn't
> have a JIT compiler.
>
> The patch is for the most recent libwebkitgtk-3.0-0 package of Wheezy.
> The patch doesn't change anything on archs other than ia64.
>
>
> The packages which were built with the patch of this bug report and the one
> of bug#694971 is here; the tar contains all debs which are created by the
> libwebkitgtk-3.0-0 source:
> http://www.fs-driver.org/debian-ia64/webkitgtk-debs.tar
>
>
> The patches also fix bug#582774 (seed FTBFS on ia64).
>
> Stephan
>
>
>
More information about the Pkg-webkit-maintainers
mailing list