Skip navigation

Release: 2.4 Previous Releases
Publish Date: October, 2007

Article Rating?


Gotchas

Introduction

We strive to make Terracotta as transparent as possible and we are constantly improving our transparency and usability, but there are still some things which may seem unintuitive at first glance.

This document seeks to highlight some of these issues and potential solutions for them.

Patterns

Lock-Then-Share

Terracotta requires that you acquire a shared lock before making changes to shared objects. Normally this is done by synchronizing on a shared object. However, there is a recurring pattern that seems like it should work, but doesn't: synchronizing on an object before it is shared and then modifying shared objects.

Because you're synchronizing on an object that later becomes shared, it may look like you are acquiring a shared lock, but, at the time you synchronize on it, it isn't shared so there is no shared lock acquisition.

If you want to acquire a shared lock, the object you are synchronizing on must already be shared at the time you synchronize on it.

Multiple Initialization

TODO: Describe the problem where a data structure is initialized at startup in the single-JVM case. When that data structure is shared across JVMs, that code needs usually needs to be modified to check first to see if the data structure has already been initialized.

Class API Issues

Mutable Enums

TODO: Describe that changes to enumerations aren't clustered (DSO behavior mimics their out-of-the-box serialization/deserialization behavior)

java.lang.ref.Reference

If user code has a java.lang.ref.Reference to a shared object Foo, Foo can be paged out of memory by the DSO reaper. The reference will be nulled out.

This behavior may be surprising to some user code. The expectation is that the reference value won't become null until the object has entered some phase of the garbage collection cycle.

See http://jira.terracotta.org/jira/browse/CDV-330 for more information.

Iterator Instances

Explicit sharing of iterator instances is not supported. Iterators created from shared collections are not problematic, but again, these iterator instances themselves cannot be shared objects (only the underlying collection)

Configuration and Setup Issues

Autolocking Collections

TODO: Describe how collections in java.util.* aren't automatically autolocked for performance reasons.

IBM JDK

There are some known issues with the IBM JDK. See Integrations IBM JDK for details.

Uninstrumented access to shared objects

Reading and writing to objects shared in Terracotta from uninstrumented methods can be problematic under certain conditions. The first involves reading/writing accessible fields of a shared object from uninstrumented code.

For example, lets say you have two classes (A and B) in the same package. Class A has an accessible field (foo). Class A is instrumented, but class B is not.

class A {
  Object foo;
}

class B {
  int m(A a) {
    if (a.foo == this) {
      a.foo = null;
  }
}

In the classes above, the reads and writes of the accessible "foo" field of class A will not function correctly for shared A instances if class B is not instrumented. The effect of the uninstrumented read usually a NullPointerException, but you could also observe old/stale values as well (not just nulls). An uninstrumented write from B.foo() will bypass Terracotta only mutating this VM's local A instance (the clustered state will not be updated). Fortunately well encapsulated classes (ie. private fields) avoid these issues.

A similar problem can happen with arrays (ie. uninstrumented code reads/writes a shared array instance).

Debuggers

Using the debugger, one can observe field values of shared objects to have phantom null values (or null element values in a array). This is a side effect of the just-in-time lazy loading and dynamic memory management features in DSO. Although a field can appear null in the debugger view, your application will see the correct values when/if the fields are read. The main issue here is that the debugger uses non-bytecode means of viewing object state. Stepping over some code that reads the phantom null field will cause the value to be resolved. Although it might be obvious, using the debugger to mutate a field of shared object will bypass Terracotta leaving your locals in an inconsistent state with the cluster.

Hidden references in anonymous and non-static inner classes

The java compiler generates a synthetic reference back to the enclosing instance for anonymous and non-static inner classes. For example consider this code:

class A {
   Runnable foo() {
     return new Runnable() {
       public void run() {  }
     }
   }

   class Inner {
     //
   }

In both the non-static inner class named "Inner" and the anonymous inner class in the "foo" method, the compiler introduced as synthetic field named "this$0" containing a reference to the enclosing A instance.

This hidden reference become significant in Terracotta when trying to share inner class instances since the enclosing type must be portable, and the enclosing instance will become shared as well.

Appendix

Contacting Terracotta


Contact Terracotta at the following:
Web site:  http://www.terracotta.org
Online forums:  http://forums.terracottatech.com/forums/
Information:  info@terracottatech.com

Platform Support

See Platform Support for information on which platforms are supported by Terracotta.
See Integrations to see the status of integrations with third-party technologies.


Copyright Information

Copyright © 2005-2007
Terracotta, Inc.
All Rights Reserved

This publication (the "Documentation") and the Terracotta software which it describes (the "Software") are protected to the maximum extent permitted under applicable law, including but not limited to, the regulations set forth in Title 17 of the United States Code, and California law. This Documentation, or any parts thereof, may not be reproduced in any form, by any method, for any purpose, without the express written consent of Terracotta. Terracotta makes no warranty, either express or implied, including but not limited to any implied warranties of merchantability or fitness for a particular purpose, with respect to the Software discussed in this Documentation, and the Documentation itself (collectively, "the Materials"). The Materials are made available solely on an "as-is" basis. In no event shall Terracotta be liable to anyone for special, collateral, incidental, indirect, punitive, exemplary, or consequential damages in connection with, or arising from the purchase or use of, the Materials. Under no circumstances and regardless of the cause of action alleged, shall Terracotta's liability exceed the purchase price of the Software described herein. Terracotta reserves the right to revise and improve its Software and Documentation as it deems fit. The Documentation describes the state of the Software at the time of publication.

Trademarks
"Terracotta," the stylized "T" logo, and "Open Terracotta" are trademarks of Terracotta. All other brand names, product names, or trademarks belong to their respective holders. Java and all Java-based trademarks and logos are trademarks or registered trademarks of Sun Microsystems, Inc. in the United States and other countries. All other brand names, product names, or trademarks belong to their respective holders.

Government Use
Use, duplication, or disclosure by the U.S. Government is subject to restrictions as set forth in FAR 12.212 (Commercial Computer Software-Restricted Rights) and DFAR 267.7202 (Rights in Technical Data and Computer Software), as applicable.

Adaptavist Theme Builder Powered by Atlassian Confluence