Program: 32825
Project: 32825
Buggy source:
/** 
 * For implementing the ListEventListener interface. When the underlying list changes, this notification allows the object to repaint itself or update itself as necessary. <p>This is implemented in two phases. First, the unsorted index tree is updated so that it maches the source list. This is necessary so that when sorted operations are performed, the comparisons are done with respect to the correct unsorted index. In the second phase, the sorted list is updated with the changes.
 */
public void listChanged(ListEvent listChanges){
  if (debug)   System.out.println("String_Node_Str");
  if (debug)   System.out.println("String_Node_Str" + listChanges);
  updates.beginEvent();
  LinkedList insertNodes=new LinkedList();
  LinkedList updateNodes=new LinkedList();
  LinkedList deleteIndices=new LinkedList();
  ListEvent firstPass=new ListEvent(listChanges);
  while (firstPass.next()) {
    int unsortedIndex=firstPass.getIndex();
    int changeType=firstPass.getType();
    if (changeType == ListEvent.INSERT) {
      IndexedTreeNode unsortedNode=unsorted.addByNode(unsortedIndex,this);
      insertNodes.addLast(unsortedNode);
    }
 else     if (changeType == ListEvent.DELETE) {
      IndexedTreeNode unsortedNode=unsorted.getNode(unsortedIndex);
      unsortedNode.removeFromTree();
      int deleteSortedIndex=deleteByUnsortedNode(unsortedNode);
      updates.addDelete(deleteSortedIndex);
    }
 else     if (changeType == ListEvent.UPDATE) {
    }
  }
  ListEvent secondPass=listChanges;
  while (secondPass.next()) {
    int unsortedIndex=secondPass.getIndex();
    int changeType=secondPass.getType();
    if (changeType == ListEvent.UPDATE) {
      IndexedTreeNode unsortedNode=unsorted.getNode(unsortedIndex);
      int deleteSortedIndex=deleteByUnsortedNode(unsortedNode);
      updateNodes.addLast(unsortedNode);
      deleteIndices.addLast(new Integer(deleteSortedIndex));
    }
  }
  if (debug)   System.out.println(deleteIndices);
  while (!updateNodes.isEmpty()) {
    IndexedTreeNode updateNode=(IndexedTreeNode)updateNodes.removeFirst();
    int deletedIndex=((Integer)deleteIndices.removeFirst()).intValue();
    int insertedIndex=insertByUnsortedNode(updateNode);
    if (debug)     System.out.println("String_Node_Str" + deletedIndex + "String_Node_Str"+ insertedIndex+ "String_Node_Str"+ deleteIndices);
    for (ListIterator i=deleteIndices.listIterator(deleteIndices.size()); i.hasPrevious(); ) {
      int currentDeletedIndex=((Integer)i.previous()).intValue();
      if (currentDeletedIndex <= insertedIndex) {
        insertedIndex++;
      }
 else {
        currentDeletedIndex++;
        i.set(new Integer(currentDeletedIndex));
      }
    }
    if (deletedIndex == insertedIndex) {
      if (debug == true)       System.out.println("String_Node_Str" + insertedIndex);
      updates.addUpdate(insertedIndex);
    }
 else {
      if (debug == true)       System.out.println("String_Node_Str" + deletedIndex + "String_Node_Str"+ insertedIndex);
      updates.addDelete(deletedIndex);
      updates.addInsert(insertedIndex);
    }
  }
  while (!insertNodes.isEmpty()) {
    IndexedTreeNode insertNode=(IndexedTreeNode)insertNodes.removeFirst();
    int insertedIndex=insertByUnsortedNode(insertNode);
    updates.addInsert(insertedIndex);
  }
  updates.commitEvent();
  if (debug)   System.out.println("String_Node_Str");
}

Fixed version (ground truth):
/** 
 * For implementing the ListEventListener interface. When the underlying list changes, this notification allows the object to repaint itself or update itself as necessary. <p>This is implemented in two phases. First, the unsorted index tree is updated so that it maches the source list. This is necessary so that when sorted operations are performed, the comparisons are done with respect to the correct unsorted index. In the second phase, the sorted list is updated with the changes.
 */
public void listChanged(ListEvent listChanges){
  if (debug)   System.out.println("String_Node_Str");
  if (debug)   System.out.println("String_Node_Str" + listChanges);
  updates.beginEvent();
  LinkedList insertNodes=new LinkedList();
  ListEvent firstPass=new ListEvent(listChanges);
  while (firstPass.next()) {
    int unsortedIndex=firstPass.getIndex();
    int changeType=firstPass.getType();
    if (changeType == ListEvent.INSERT) {
      IndexedTreeNode unsortedNode=unsorted.addByNode(unsortedIndex,this);
      insertNodes.addLast(unsortedNode);
    }
 else     if (changeType == ListEvent.DELETE) {
      IndexedTreeNode unsortedNode=unsorted.getNode(unsortedIndex);
      unsortedNode.removeFromTree();
      int deleteSortedIndex=deleteByUnsortedNode(unsortedNode);
      updates.addDelete(deleteSortedIndex);
    }
 else     if (changeType == ListEvent.UPDATE) {
    }
  }
  if (debug) {
    System.out.print("String_Node_Str");
    for (int i=0; i < sorted.size(); i++) {
      System.out.print("String_Node_Str" + i);
      int unsortedIndex=((IndexedTreeNode)sorted.getNode(i).getValue()).getIndex();
      System.out.print("String_Node_Str" + unsortedIndex);
      System.out.print("String_Node_Str" + source.get(unsortedIndex) + "String_Node_Str");
    }
    System.out.print("String_Node_Str");
  }
  IndicesPendingDeletion indicesPendingDeletion=new IndicesPendingDeletion();
  ListEvent secondPass=new ListEvent(listChanges);
  while (secondPass.next()) {
    int unsortedIndex=secondPass.getIndex();
    int changeType=secondPass.getType();
    if (changeType == ListEvent.UPDATE) {
      IndexedTreeNode unsortedNode=unsorted.getNode(unsortedIndex);
      IndexedTreeNode sortedNode=(IndexedTreeNode)unsortedNode.getValue();
      int originalIndex=sortedNode.getIndex();
      indicesPendingDeletion.addPair(new IndexNodePair(originalIndex,unsortedNode));
    }
  }
  if (debug)   System.out.println("String_Node_Str" + indicesPendingDeletion);
  ListEvent thirdPass=listChanges;
  while (thirdPass.next()) {
    int unsortedIndex=thirdPass.getIndex();
    int changeType=thirdPass.getType();
    if (changeType == ListEvent.UPDATE) {
      IndexedTreeNode unsortedNode=unsorted.getNode(unsortedIndex);
      int deleteSortedIndex=deleteByUnsortedNode(unsortedNode);
    }
  }
  while (indicesPendingDeletion.hasPair()) {
    IndexNodePair indexNodePair=indicesPendingDeletion.removePair();
    int insertedIndex=insertByUnsortedNode(indexNodePair.node);
    int deletedIndex=indexNodePair.index;
    insertedIndex=indicesPendingDeletion.adjustDeleteAndInsert(deletedIndex,insertedIndex);
    if (debug)     System.out.println("String_Node_Str" + deletedIndex + "String_Node_Str"+ insertedIndex+ "String_Node_Str"+ indicesPendingDeletion);
    if (deletedIndex == insertedIndex) {
      if (debug == true)       System.out.println("String_Node_Str" + insertedIndex);
      updates.addUpdate(insertedIndex);
    }
 else {
      if (debug == true)       System.out.println("String_Node_Str" + deletedIndex + "String_Node_Str"+ insertedIndex);
      updates.addDelete(deletedIndex);
      updates.addInsert(insertedIndex);
    }
  }
  while (!insertNodes.isEmpty()) {
    IndexedTreeNode insertNode=(IndexedTreeNode)insertNodes.removeFirst();
    int insertedIndex=insertByUnsortedNode(insertNode);
    updates.addInsert(insertedIndex);
  }
  updates.commitEvent();
  if (debug)   System.out.println("String_Node_Str");
}