Re: Odd test failure in mock (& sometimes koji)

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 09/27/2015 09:45 PM, Gerard Ryan wrote:
> Hi,
> 
> I'm encountering a test failure for the minimal-json package in mock,
> and I'm hoping someone can help me understand it. The assertions that
> fail are at [1].
> 
> If I take one of the assertions as an example, the first one on line 44:
> 
> assertSame(Json.NULL, JsonValue.NULL);
> 
> This is trying to assert that both of the objects refer to the same
> objects in memory. I think this is a perfectly fine thing to expect in
> this case, since the NULL field in JsonValue[3] refers directly to the
> NULL field in the Json class[4].
> 
> The test works fine if I just run mvn test in the upstream project, and
> I'm not applying any patches or changes in the spec file[2].
> 
> To compound my confusion, where this doesn't work in local mock for me
> at all for any release (f24, f23,f22), it works in koji **sometimes**:
> 
> * a passing build from a couple of weeks ago in rawhide[5]
> * a passing scratch build from just now in rawhide[6]
> * a failing scratch build from just now in f23 [7]
> * a passing scratch build from just now in f23 [8]
> 
> I _assume_ that my consistent failures locally and the intermittent
> failures in koji are related.
> 
> If anyone has any idea what the cause of this is (also, solution ;)),
> I'd be delighted for any advice. I've been out of the Java head space
> for 6+ months now, so it's very possible that I'm overlooking something
> something obvious!

It's a race condition - bug in upstream code. You can get different
results depending on the order of initialization of Json and JsonValue
classes.

Consider the following example:

    class A {
      static B x = new B();
    }

    class B {
      static B x = A.x;
    }

    public class Main {
      public static void main(String[] args) {
        System.out.println(A.x == B.x);
      }
    }

What do you think the above program will print when executed? "true"?
Wrong. It prints "false".

That's not all, try swapping arguments of comparison operator (i.e
replace "A.x == B.x" with "B.x == A.x"). Now it prints "true"! Magic? :)

In case it's still not clear, this is how "false" result is produced:

1. JVM starts initializing class A. All fields are initially filled with
zeros. A.x is null at this point.
2. JVM starts executing static field initializer for class A. It sees
reference to class B.
3. JVM starts initializing class B. It then executes static field
initializer for class B - B.x is set to A.x, which is null.
4. JVM continues with running static field initializer for class A. New
instance of class B is created and assigned to A.x

End result: B.x is null, A.x is not null.

-- 
Mikolaj Izdebski
Software Engineer, Red Hat
IRC: mizdebsk
--
java-devel mailing list
java-devel@xxxxxxxxxxxxxxxxxxxxxxx
https://admin.fedoraproject.org/mailman/listinfo/java-devel




[Index of Archives]     [Red Users]     [Fedora Desktop]     [Fedora SELinux]     [Big List of Linux Books]     [Yosemite News]     [KDE Users]

  Powered by Linux