uima-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From sc...@apache.org
Subject svn commit: r706304 - in /incubator/uima/uimaj/trunk/uimaj-core/src: main/java/org/apache/uima/cas/impl/ main/java/org/apache/uima/util/ test/java/org/apache/uima/cas/test/
Date Mon, 20 Oct 2008 14:22:11 GMT
Author: schor
Date: Mon Oct 20 07:22:11 2008
New Revision: 706304

URL: http://svn.apache.org/viewvc?rev=706304&view=rev
Log:
[UIMA-1207] patch applied, with change: made "enum" in casImpl "private", and changed CasPool getCas to not make and throw away Date objects, just to get the current time - used System.currentTimeMillisec method instead.  uimaj-core tests run ok.

Modified:
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASImpl.java
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASSerializer.java
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Heap.java
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/MarkerImpl.java
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Serialization.java
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/StringHeap.java
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/XmiCasSerializer.java
    incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/util/CasPool.java
    incubator/uima/uimaj/trunk/uimaj-core/src/test/java/org/apache/uima/cas/test/SerializationReinitTest.java

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASImpl.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASImpl.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASImpl.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASImpl.java Mon Oct 20 07:22:11 2008
@@ -135,6 +135,7 @@
     new DebugFSLogicalStructure();
   }
 
+  private static enum ModifiedHeap { FSHEAP, BYTEHEAP, SHORTHEAP, LONGHEAP };
   // Static classes representing shared instance data
   // - shared data is computed once
 
@@ -211,6 +212,14 @@
     private MarkerImpl trackingMark;
     
     private IntVector modifiedPreexistingFSs;
+    
+    private IntVector modifiedFSHeapCells;
+    
+    private IntVector modifiedByteHeapCells;
+    
+    private IntVector modifiedShortHeapCells;
+    
+    private IntVector modifiedLongHeapCells;
 
     private SharedViewData(boolean useFSCache) {
       this.useFSCache = useFSCache;
@@ -324,6 +333,10 @@
     
     this.svd.trackingMark = null;
     this.svd.modifiedPreexistingFSs = null; 
+    this.svd.modifiedFSHeapCells = null;
+    this.svd.modifiedByteHeapCells = null;
+    this.svd.modifiedShortHeapCells = null;
+    this.svd.modifiedLongHeapCells = null;
   }
 
   /**
@@ -910,6 +923,10 @@
     
     this.svd.trackingMark = null;
     this.svd.modifiedPreexistingFSs = null;
+    this.svd.modifiedFSHeapCells = null;
+    this.svd.modifiedByteHeapCells = null;
+    this.svd.modifiedShortHeapCells = null;
+    this.svd.modifiedLongHeapCells = null;
   }
 
   /**
@@ -1065,6 +1082,10 @@
     // this.sofa2jcasMap.clear();
     this.svd.trackingMark = null;
     this.svd.modifiedPreexistingFSs = null;
+    this.svd.modifiedFSHeapCells = null;
+    this.svd.modifiedByteHeapCells = null;
+    this.svd.modifiedShortHeapCells = null;
+    this.svd.modifiedLongHeapCells = null;
   }
 
   void reinit(int[] heapMetadata, int[] heapArray, String[] stringTable, int[] fsIndex,
@@ -1100,7 +1121,7 @@
       this.svd.baseCAS.reinit(istream);
       return;
     }
-    this.resetNoQuestions();
+   
     DataInputStream dis = new DataInputStream(istream);
 
     try {
@@ -1118,17 +1139,23 @@
         swap = true;
       }
 
-      // version
-      // NOTE: even though nothing ever uses the version (yet),
-      // we MUST read it from the stream or else subsequent
-      // reads will not work. So that's why
-      // we are reading here and not assigning to any variable.
+      // version      
+      // version 2 indicates this is in delta format.
+      int version;
       if (swap) {
-        swap4(dis, bytebuf);
+        version = swap4(dis, bytebuf);
       } else {
-        dis.readInt();
+        version = dis.readInt();
       }
-
+      
+      boolean delta = false;
+      if (version == 2)  {
+        delta = true;
+      }
+      if (!delta) {
+        this.resetNoQuestions();
+      }
+      
       // main fsheap
       int fsheapsz = 0;
       if (swap) {
@@ -1136,16 +1163,23 @@
       } else {
         fsheapsz = dis.readInt();
       }
-
-      this.getHeap().reinitSizeOnly(fsheapsz);
-      for (int i = 0; i < fsheapsz; i++) {
+      
+      int startPos = 0;
+      if (!delta) {
+        this.getHeap().reinitSizeOnly(fsheapsz);
+      } else {
+    	startPos = this.getHeap().getNextId();
+    	this.getHeap().grow(fsheapsz);
+      }
+      
+      for (int i = startPos; i < fsheapsz+startPos; i++) {
         if (swap) {
           this.getHeap().heap[i] = swap4(dis, bytebuf);
         } else {
           this.getHeap().heap[i] = dis.readInt();
         }
       }
-
+      
       // string heap
       int stringheapsz = 0;
       if (swap) {
@@ -1201,7 +1235,24 @@
       }
       shdh.refHeapPos = refheapsz + StringHeapDeserializationHelper.FIRST_CELL_REF;
       
-      this.getStringHeap().reinit(shdh);
+      this.getStringHeap().reinit(shdh, delta);
+      
+      //if delta, handle modified fs heap cells
+      if (delta) {
+        int fsmodssz = 0;
+        if (swap) {
+          fsmodssz = swap4(dis, bytebuf);
+        } else {
+          fsmodssz = dis.readInt();
+        }
+        for (int i = 0; i < fsmodssz; i++) {
+          if (swap) {
+            this.getHeap().heap[swap4(dis,bytebuf)] = swap4(dis, bytebuf);
+          } else {
+            this.getHeap().heap[dis.readInt()] = dis.readInt();
+          }
+        }
+      }
 
       // indexed FSs
       int fsindexsz = 0;
@@ -1220,8 +1271,12 @@
       }
 
       // build the index
-      reinitIndexedFSs(fsindexes);
-
+      if (delta) {
+    	reinitDeltaIndexedFSs(fsindexes);  
+      } else {
+        reinitIndexedFSs(fsindexes);
+      }
+      
       // byte heap
       int byteheapsz = 0;
       if (swap) {
@@ -1230,14 +1285,20 @@
         byteheapsz = dis.readInt();
       }
 
-      this.getByteHeap().heap = new byte[Math.max(16, byteheapsz)]; // must
-      // be >
-      // 0
-      for (int i = 0; i < byteheapsz; i++) {
-        this.getByteHeap().heap[i] = dis.readByte();
+      if (!delta) {
+        this.getByteHeap().heap = new byte[Math.max(16, byteheapsz)]; // must
+        // be >
+        // 0
+        for (int i = 0; i < byteheapsz; i++) {
+          this.getByteHeap().heap[i] = dis.readByte();
+        }
+        this.getByteHeap().heapPos = byteheapsz;
+      }  else {
+        for (int i=0; i < byteheapsz; i++) {
+    	  this.getByteHeap().addByte(dis.readByte());
+        }
+        this.getByteHeap().heapPos += byteheapsz;
       }
-      this.getByteHeap().heapPos = byteheapsz;
-
       // word alignment
       int align = (4 - (byteheapsz % 4)) % 4;
       for (int i = 0; i < align; i++) {
@@ -1251,18 +1312,29 @@
       } else {
         shortheapsz = dis.readInt();
       }
-      this.getShortHeap().heap = new short[Math.max(16, shortheapsz)]; // must
-      // be >
-      // 0
-      for (int i = 0; i < shortheapsz; i++) {
-        if (swap) {
-          this.getShortHeap().heap[i] = (short) swap2(dis, bytebuf);
-        } else {
-          this.getShortHeap().heap[i] = dis.readShort();
+      
+      if (!delta) {
+        this.getShortHeap().heap = new short[Math.max(16, shortheapsz)]; // must
+        // be >
+        // 0
+        for (int i = 0; i < shortheapsz; i++) {
+          if (swap) {
+            this.getShortHeap().heap[i] = (short) swap2(dis, bytebuf);
+          } else {
+            this.getShortHeap().heap[i] = dis.readShort();
+          }
         }
+        this.getShortHeap().heapPos = shortheapsz;
+      } else {
+    	for (int i = 0; i < shortheapsz; i++) {
+          if (swap) {
+            this.getShortHeap().addShort((short) swap2(dis, bytebuf));
+          } else {
+            this.getShortHeap().addShort(dis.readShort());
+          }
+         }
+    	 this.getShortHeap().heapPos += shortheapsz;
       }
-      this.getShortHeap().heapPos = shortheapsz;
-
       // word alignment
       if (shortheapsz % 2 != 0) {
         dis.readShort();
@@ -1276,18 +1348,110 @@
       } else {
         longheapsz = dis.readInt();
       }
-      this.getLongHeap().heap = new long[Math.max(16, longheapsz)]; // must
-      // be >
-      // 0
-      for (int i = 0; i < longheapsz; i++) {
-        if (swap) {
-          this.getLongHeap().heap[i] = swap8(dis, bytebuf);
+      
+      if (!delta) {
+        this.getLongHeap().heap = new long[Math.max(16, longheapsz)]; // must
+        // be >
+        // 0
+        for (int i = 0; i < longheapsz; i++) {
+          if (swap) {
+            this.getLongHeap().heap[i] = swap8(dis, bytebuf);
+          } else {
+            this.getLongHeap().heap[i] = dis.readLong();
+          }
+        }
+        this.getLongHeap().heapPos = longheapsz;
+      } else {
+    	for (int i = 0; i < longheapsz; i++) {
+          if (swap) {
+            this.getLongHeap().addLong( swap8(dis, bytebuf));
+          } else {
+            this.getLongHeap().addLong(dis.readLong());
+          }
+        }
+    	this.getLongHeap().heapPos += longheapsz;
+      }
+      
+      if (delta)  {
+        //modified Byte Heap
+    	if (swap) {
+    	  byteheapsz = swap4(dis, bytebuf);
+    	} else {
+    	  byteheapsz = dis.readInt();
+    	}
+    	if (byteheapsz > 0) {
+    	  int[] byteHeapAddrs = new int[byteheapsz];
+    	  for (int i=0; i < byteheapsz; i++) {
+    		if (swap) {
+    	      byteHeapAddrs[i] = swap4(dis, bytebuf);
+    	    } else {
+    	      byteHeapAddrs[i] = dis.readInt();
+    	    }
+    	  }
+    	  for (int i=0; i < byteheapsz; i++) {
+    	    this.getByteHeap().heap[byteHeapAddrs[i]] = dis.readByte();
+    	  }
+    	}
+    	// word alignment
+        align = (4 - (byteheapsz % 4)) % 4;
+        for (int i = 0; i < align; i++) {
+          dis.readByte();
+        }
+        
+        //modified Short Heap
+    	if (swap) {
+      	  shortheapsz = swap4(dis, bytebuf);
+      	} else {
+      	  shortheapsz = dis.readInt();
+      	}
+      	if (shortheapsz > 0) {
+      	  int[] shortHeapAddrs = new int[shortheapsz];
+      	  for (int i=0; i < shortheapsz; i++) {
+      		if (swap) {
+      	      shortHeapAddrs[i] = swap4(dis, bytebuf);
+      	    } else {
+      	      shortHeapAddrs[i] = dis.readInt();
+      	    }
+      	  }
+      	  for (int i=0; i < shortheapsz; i++) {
+      		if (swap) {
+              this.getShortHeap().heap[i] = (short) swap2(dis, bytebuf);
+            } else {
+              this.getShortHeap().heap[i] = dis.readShort();
+            }
+      	  }
+      	}
+      	
+        // word alignment
+        if (shortheapsz % 2 != 0) {
+          dis.readShort();
+        }
+      
+        //modified Long Heap
+      	if (swap) {
+          longheapsz = swap4(dis, bytebuf);
         } else {
-          this.getLongHeap().heap[i] = dis.readLong();
+          longheapsz = dis.readInt();
         }
+        if (longheapsz > 0) {
+          int[] longHeapAddrs = new int[shortheapsz];
+          for (int i=0; i < shortheapsz; i++) {
+        	if (swap) {
+        	  longHeapAddrs[i] = swap4(dis, bytebuf);
+        	} else {
+        	  longHeapAddrs[i] = dis.readInt();
+        	}
+          }
+          for (int i=0; i < longheapsz; i++) {
+        	if (swap) {
+              this.getLongHeap().heap[i] = (short) swap8(dis, bytebuf);
+            } else {
+              this.getLongHeap().heap[i] = dis.readLong();
+            }
+          }
+        }
+    	
       }
-      this.getLongHeap().heapPos = longheapsz;
-
     } catch (IOException e) {
       CASRuntimeException exception = new CASRuntimeException(
           CASRuntimeException.BLOB_DESERIALIZATION, new String[] { e.getMessage() });
@@ -1358,6 +1522,7 @@
       iterator.moveToNext();
     }
     this.svd.viewCount = numViews; // total number of views
+    
     for (int viewNbr = 1; viewNbr <= numViews; viewNbr++) {
       CAS view = (viewNbr == 1) ? getInitialView() : getView(viewNbr);
       if (view != null) {
@@ -1373,6 +1538,65 @@
       }
     }
   }
+  
+  // fsIndex contains added, removed and reindexed FS per view
+  private void reinitDeltaIndexedFSs(int[] fsIndex) {
+	// Add FSs to index repository for base CAS
+	int numViews = fsIndex[0]; //total number of views
+	int loopLen = fsIndex[1]; // number of sofas, not necessarily the same as
+	// number of views. Should only contain new Sofas. 
+	for (int i = 2; i < loopLen + 2; i++) { // iterate over all the sofas,
+	  this.indexRepository.addFS(fsIndex[i]); // add to base index
+	}
+	int loopStart = loopLen + 2;
+
+	FSIterator iterator = this.svd.baseCAS.getSofaIterator();
+	final Feature idFeat = getTypeSystem().getFeatureByFullName(CAS.FEATURE_FULL_NAME_SOFAID);
+	// Add FSs to index repository for each View
+	while (iterator.isValid()) {
+	      SofaFS sofa = (SofaFS) iterator.get();
+	      String id = getLowLevelCAS().ll_getStringValue(((FeatureStructureImpl) sofa).getAddress(),
+	          ((FeatureImpl) idFeat).getCode());
+	      if (CAS.NAME_DEFAULT_SOFA.equals(id)) {
+	        this.registerInitialSofa();
+	        this.svd.sofaNameSet.add(id);
+	      }
+	      // next line the getView as a side effect
+	      // checks for dupl sofa name, and if not,
+	      // adds the name to the sofaNameSet
+	      ((CASImpl) this.getView(sofa)).registerView(sofa);
+
+	      iterator.moveToNext();
+	}
+	this.svd.viewCount = numViews; // total number of views
+	    
+	for (int viewNbr = 1; viewNbr <= numViews; viewNbr++) {
+      CAS view = (viewNbr == 1) ? getInitialView() : getView(viewNbr);
+      if (view != null) {
+        FSIndexRepositoryImpl loopIndexRep = (FSIndexRepositoryImpl) getSofaIndexRepository(viewNbr);
+        loopLen = fsIndex[loopStart];
+        for (int i = loopStart + 1; i < loopStart + 1 + loopLen; i++) {
+          loopIndexRep.addFS(fsIndex[i]);
+        }
+        loopStart += loopLen + 1;
+        loopLen = fsIndex[loopStart];
+        for (int i = loopStart + 1; i < loopStart + 1 + loopLen; i++) {
+          loopIndexRep.removeFS(fsIndex[i]);
+        }
+        loopStart += loopLen + 1;
+        loopLen = fsIndex[loopStart];
+        for (int i = loopStart + 1; i < loopStart + 1 + loopLen; i++) {
+          loopIndexRep.removeFS(fsIndex[i]);
+          loopIndexRep.addFS(fsIndex[i]);
+        }
+        loopStart += loopLen + 1;
+        ((CASImpl) view).updateDocumentAnnotation();
+      } else {
+        loopStart += 1;
+      }
+	}
+	    
+  }
 
   // IndexedFSs format:
   // number of views
@@ -1411,6 +1635,71 @@
     }
     return v.toArray();
   }
+  
+  
+  //Delta IndexedFSs format:
+  // number of views
+  // number of sofas - new
+  // [sofa-1 ... sofa-n]
+  // number of new FS add in View1
+  // [FS-1 ... FS-n]
+  // number of  FS removed from View1
+  // [FS-1 ... FS-n]
+  //number of  FS reindexed in View1
+  // [FS-1 ... FS-n]
+  // etc.
+  int[] getDeltaIndexedFSs(MarkerImpl mark) {
+    IntVector v = new IntVector();
+    int[] fsLoopIndex;
+    int[] fsDeletedFromIndex;
+    int[] fsReindexed;
+
+    int numViews = getBaseSofaCount();
+    v.add(numViews);
+
+    // Get indexes for base CAS
+    fsLoopIndex = this.svd.baseCAS.indexRepository.getIndexedFSs();
+    // Get the new Sofa FS
+    IntVector newSofas = new IntVector();
+    for (int k = 0; k < fsLoopIndex.length; k++) {
+      if ( mark.isNew(fsLoopIndex[k]) ) {
+        newSofas.add(fsLoopIndex[k]);
+      }
+    }
+    
+    v.add(newSofas.size());
+    for (int k = 0; k < newSofas.size(); k++) {
+      v.add(newSofas.get(k));
+    }
+
+    // Get indexes for each SofaFS in the CAS
+    for (int sofaNum = 1; sofaNum <= numViews; sofaNum++) {
+      FSIndexRepositoryImpl loopIndexRep = (FSIndexRepositoryImpl) this.svd.baseCAS
+          .getSofaIndexRepository(sofaNum);
+      if (loopIndexRep != null) {
+        fsLoopIndex = loopIndexRep.getAddedFSs();
+        fsDeletedFromIndex = loopIndexRep.getDeletedFSs();
+        fsReindexed = loopIndexRep.getReindexedFSs();
+      } else {
+        fsLoopIndex = (new IntVector()).toArray();
+        fsDeletedFromIndex = (new IntVector()).toArray();
+        fsReindexed = (new IntVector()).toArray();
+      }
+      v.add(fsLoopIndex.length);
+      for (int k = 0; k < fsLoopIndex.length; k++) {
+        v.add(fsLoopIndex[k]);
+      }
+      v.add(fsDeletedFromIndex.length);
+      for (int k = 0; k < fsDeletedFromIndex.length; k++) {
+        v.add(fsDeletedFromIndex[k]);
+      }
+      v.add(fsReindexed.length);
+      for (int k = 0; k < fsReindexed.length; k++) {
+        v.add(fsReindexed[k]);
+      }
+    }
+    return v.toArray();
+  }
 
   void createStringTableFromArray(String[] stringTable) {
     // why a new heap instead of reseting the old one???
@@ -1498,7 +1787,7 @@
     }
     this.getHeap().heap[addr + arrayContentOffset + index] = value;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(addr);
+    	this.logFSUpdate(addr, addr+arrayContentOffset+index, ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -1581,7 +1870,7 @@
     final int offset = addr + arrayContentOffset;
     System.arraycopy(src, srcOffset, this.getHeap().heap, offset + destOffset, length);
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(addr);
+    	this.logFSUpdate(addr, offset + destOffset, ModifiedHeap.FSHEAP, length);
     }
   }
 
@@ -1647,7 +1936,8 @@
   public void setFeatureValue(int addr, int feat, int val) {
     this.getHeap().heap[(addr + this.svd.casMetadata.featureOffset[feat])] = val;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(addr);
+    	this.logFSUpdate(addr, addr+this.svd.casMetadata.featureOffset[feat], 
+    			ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -2855,14 +3145,16 @@
   public final void ll_setIntValue(int fsRef, int featureCode, int value) {
     this.getHeap().heap[fsRef + this.svd.casMetadata.featureOffset[featureCode]] = value;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, fsRef +  this.svd.casMetadata.featureOffset[featureCode],
+    			ModifiedHeap.FSHEAP, 1);
     }
   }
 
   public final void ll_setFloatValue(int fsRef, int featureCode, float value) {
     this.getHeap().heap[fsRef + this.svd.casMetadata.featureOffset[featureCode]] = float2int(value);
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, fsRef +  this.svd.casMetadata.featureOffset[featureCode],
+    			ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -2882,14 +3174,16 @@
     final int valueAddr = fsRef + this.svd.casMetadata.featureOffset[featureCode];
     this.getHeap().heap[valueAddr] = stringAddr;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, fsRef +  this.svd.casMetadata.featureOffset[featureCode],
+    			ModifiedHeap.FSHEAP, 1);
     }
   }
 
   public final void ll_setRefValue(int fsRef, int featureCode, int value) {
     this.getHeap().heap[fsRef + this.svd.casMetadata.featureOffset[featureCode]] = value;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, fsRef +  this.svd.casMetadata.featureOffset[featureCode],
+    			ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3115,7 +3409,7 @@
     final int pos = getArrayStartAddress(fsRef) + position;
     this.getHeap().heap[pos] = value;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, pos, ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3123,7 +3417,7 @@
     final int pos = getArrayStartAddress(fsRef) + position;
     this.getHeap().heap[pos] = float2int(value);
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, pos,ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3132,7 +3426,7 @@
     final int stringCode = (value == null) ? NULL : addString(value);
     this.getHeap().heap[pos] = stringCode;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, pos, ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3140,7 +3434,7 @@
     final int pos = getArrayStartAddress(fsRef) + position;
     this.getHeap().heap[pos] = value;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, pos, ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3363,7 +3657,7 @@
     this.getHeap().heap[fsRef + this.svd.casMetadata.featureOffset[featureCode]] = value ? CASImpl.TRUE
         : CASImpl.FALSE;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+      this.logFSUpdate(fsRef, fsRef + this.svd.casMetadata.featureOffset[featureCode], ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3377,7 +3671,7 @@
   public final void ll_setByteValue(int fsRef, int featureCode, byte value) {
     this.getHeap().heap[fsRef + this.svd.casMetadata.featureOffset[featureCode]] = value;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+      this.logFSUpdate(fsRef, fsRef + this.svd.casMetadata.featureOffset[featureCode], ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3391,7 +3685,7 @@
   public final void ll_setShortValue(int fsRef, int featureCode, short value) {
     this.getHeap().heap[fsRef + this.svd.casMetadata.featureOffset[featureCode]] = value;
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+      this.logFSUpdate(fsRef, fsRef + this.svd.casMetadata.featureOffset[featureCode], ModifiedHeap.FSHEAP, 1);
     }
   }
 
@@ -3492,7 +3786,7 @@
     final int offset = this.getHeap().heap[getArrayStartAddress(fsRef)];
     this.getByteHeap().setHeapValue(value, offset + position);
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+    	this.logFSUpdate(fsRef, offset+position, ModifiedHeap.BYTEHEAP, 1);
     }
   }
 
@@ -3509,7 +3803,7 @@
     final int offset = this.getHeap().heap[getArrayStartAddress(fsRef)];
     this.getByteHeap().setHeapValue(value, offset + position);
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+      this.logFSUpdate(fsRef, offset+position, ModifiedHeap.BYTEHEAP, 1);
     }
   }
 
@@ -3524,7 +3818,7 @@
     final int offset = this.getHeap().heap[getArrayStartAddress(fsRef)];
     this.getShortHeap().setHeapValue(value, offset + position);
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+      this.logFSUpdate(fsRef, offset+position, ModifiedHeap.SHORTHEAP, 1);
     }
   }
 
@@ -3539,7 +3833,7 @@
     final int offset = this.getHeap().heap[getArrayStartAddress(fsRef)];
     this.getLongHeap().setHeapValue(value, offset + position);
     if (this.svd.trackingMark != null) {
-    	this.logFSUpdate(fsRef);
+      this.logFSUpdate(fsRef, offset+position, ModifiedHeap.LONGHEAP, 1);
     }
   }
 
@@ -3940,22 +4234,63 @@
     if (!this.svd.flushEnabled) {
 	  throw new CASAdminException(CASAdminException.FLUSH_DISABLED);
 	}
-	this.svd.trackingMark = new MarkerImpl(this.getHeap().getNextId(), this);
+	this.svd.trackingMark = new MarkerImpl(this.getHeap().getNextId(), 
+			this.getStringHeap().getSize(),
+			this.getByteHeap().getSize(),
+			this.getShortHeap().getSize(),
+			this.getLongHeap().getSize(),
+			this);
 	if (this.svd.modifiedPreexistingFSs == null) {
 	  this.svd.modifiedPreexistingFSs = new IntVector();
 	}
+	if (this.svd.modifiedFSHeapCells == null) {
+	  this.svd.modifiedFSHeapCells = new IntVector();
+	}
+	if (this.svd.modifiedByteHeapCells == null) {
+      this.svd.modifiedByteHeapCells = new IntVector();
+	}
+	if (this.svd.modifiedShortHeapCells == null) { 
+      this.svd.modifiedShortHeapCells = new IntVector();
+	}
+	if (this.svd.modifiedLongHeapCells == null) {
+      this.svd.modifiedLongHeapCells = new IntVector();
+	}
 	return this.svd.trackingMark;
   }
 
-  private void logFSUpdate(int addr) {
-	if (this.svd.trackingMark != null && !this.svd.trackingMark.isNew(addr)) {
+  private void logFSUpdate(int fsaddr, int position, ModifiedHeap whichheap, int howmany) {
+	if (this.svd.trackingMark != null && !this.svd.trackingMark.isNew(fsaddr)) {
+	  //log the FS
 	  int lastModifiedFS = -1;	
 	  if (this.svd.modifiedPreexistingFSs.size() > 0) {
 	    lastModifiedFS =  this.svd.modifiedPreexistingFSs.get(this.svd.modifiedPreexistingFSs.size()-1);
 	  }
 	  //only log if the last one logged is not the same fs.s
-	  if (lastModifiedFS != addr) {
-		  this.svd.modifiedPreexistingFSs.add(addr);
+	  if (lastModifiedFS != fsaddr) {
+		this.svd.modifiedPreexistingFSs.add(fsaddr);
+	  }	
+	  //log cells that were updated
+	  switch (whichheap) {  
+		case FSHEAP:
+		  for (int i=0; i < howmany;i++) {
+		    this.svd.modifiedFSHeapCells.add(position+i);
+		  }
+		break;
+		case BYTEHEAP:
+		  for (int i=0; i < howmany;i++) {
+		    this.svd.modifiedByteHeapCells.add(position+i);
+		  }
+		break;
+		case SHORTHEAP:
+		  for (int i=0; i < howmany;i++) {
+		    this.svd.modifiedShortHeapCells.add(position+i);
+		  }
+	    break;
+		case LONGHEAP:
+		  for (int i=0; i < howmany;i++) {
+		    this.svd.modifiedLongHeapCells.add(position+i);
+		  }
+	    break;
 	  }
 	}
   }
@@ -3968,4 +4303,20 @@
 	return this.svd.modifiedPreexistingFSs;  
   }
   
+  IntVector getModifiedFSHeapAddrs() {
+	return this.svd.modifiedFSHeapCells;  
+  }
+  
+  IntVector getModifiedByteHeapAddrs() {
+		return this.svd.modifiedByteHeapCells;  
+  }
+  
+  IntVector getModifiedShortHeapAddrs() {
+		return this.svd.modifiedShortHeapCells;  
+  }
+  
+  IntVector getModifiedLongHeapAddrs() {
+		return this.svd.modifiedLongHeapCells;  
+  }
+  
 }

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASSerializer.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASSerializer.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASSerializer.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/CASSerializer.java Mon Oct 20 07:22:11 2008
@@ -27,6 +27,7 @@
 import java.util.ArrayList;
 
 import org.apache.uima.cas.CASRuntimeException;
+import org.apache.uima.cas.Marker;
 
 /**
  * Serialization for CAS. This serializes the state of the CAS, assuming that the type and index
@@ -270,6 +271,235 @@
 
   }
 
+  
+  /**
+   * Serializes only new and modified FS and index operations made after
+   * the tracking mark is created.
+   * Serizlizes CAS data in binary Delta format described below and writes it to the output stream.
+   * 
+   * ElementSize NumberOfElements Description
+   * ----------- ---------------- ---------------------------------------------------------
+   * 4				1				Blob key = "UIMA" in utf-8 (byte order flag)
+   * 4				1				Version (1 = complete cas, 2 = delta cas)
+   * 4				1				size of 32-bit heap array = s32H
+   * 4            s32H              32-bit FS heap array (new elements) 
+   * 4              1 				size of 16-bit string Heap array = sSH 
+   * 2 			   sSH 				16-bit string heap array (new strings)
+   * 4 				1 				size of string Ref Heap array = sSRH 
+   * 4 			2*sSRH				string ref offsets and lengths (for new strings)
+   * 4              1				number of modified, preexisting 32-bit modified FS heap elements = sM32H
+   * 4			2*sM32H             32-bit heap offset and value (preexisting cells modified)	 
+   * 4 	            1 				size of FS index array = sFSI 
+   * 4			  sFSI 				FS index array in Delta format
+   * 4 				1 				size of 8-bit Heap array = s8H 
+   * 1 			  s8H 				8-bit Heap array (new elements)
+   * 4 				1 				size of 16-bit Heap array = s16H
+   * 2 			  s16H 				16-bit Heap array (new elements) 
+   * 4 				1 				size of 64-bit Heap array = s64H 
+   * 8 			  s64H 				64-bit Heap array (new elements)
+   * 4				1				number of modified, preexisting 8-bit heap elements = sM8H
+   * 4			  sM8H              8-bit heap offsets (preexisting cells modified)
+   * 1			  sM8H              8-bit heap values  (preexisting cells modified)
+   * 4				1				number of modified, preexisting 16-bit heap elements = sM16H
+   * 4			  sM16H             16-bit heap offsets (preexisting cells modified)
+   * 2			  sM16H             16-bit heap values  (preexisting cells modified)
+   * 4				1				number of modified, preexisting 64-bit heap elements = sM64H
+   * 4			  sM64H             64-bit heap offsets (preexisting cells modified)
+   * 2			  sM64H             64-bit heap values  (preexisting cells modified)
+   * 
+   * 
+   * @param cas
+   * @param ostream
+   * @param trackingMark
+   */
+  public void addCAS(CASImpl cas, OutputStream ostream, Marker trackingMark) {
+
+    try {
+      MarkerImpl mark = (MarkerImpl) trackingMark;
+      DataOutputStream dos = new DataOutputStream(ostream);
+
+      // get the indexed FSs
+      this.fsIndex = cas.getDeltaIndexedFSs(mark);
+      
+      // output the key and version number
+
+      byte[] uima = new byte[4];
+      uima[0] = 85; // U
+      uima[1] = 73; // I
+      uima[2] = 77; // M
+      uima[3] = 65; // A
+
+      ByteBuffer buf = ByteBuffer.wrap(uima);
+      int key = buf.asIntBuffer().get();
+
+      int version = 2;    //1 = current full serialization; 2 = delta format 
+                          //perhaps this should be split into 2 bytes for version and 2 bytes for format.
+      dos.writeInt(key);
+      dos.writeInt(version);
+
+      // output the new FS heap cells
+      final int heapSize = cas.getHeap().getCellsUsed() - mark.nextFSId;
+      
+      dos.writeInt(heapSize);
+      for (int i = mark.nextFSId; i < cas.getHeap().getCellsUsed(); i++) {
+        dos.writeInt(cas.getHeap().heap[i]);
+      }
+
+      // output the new strings
+      StringHeapDeserializationHelper shdh = cas.getStringHeap().serialize(mark.nextStringHeapAddr);
+
+      // compute the number of total size of data in stringHeap
+      // total size = char buffer length + length of strings in the string list;
+      int stringHeapLength = shdh.charHeapPos;
+      int stringListLength = 0;
+      for (int i = 0; i < shdh.refHeap.length; i += 3) {
+        int ref = shdh.refHeap[i + StringHeapDeserializationHelper.STRING_LIST_ADDR_OFFSET];
+        // this is a string in the string list
+        // get length and add to total string heap length
+        if (ref != 0) {
+          // terminate each string with a null
+          stringListLength += 1 + cas.getStringHeap().getStringForCode(ref).length();
+        }
+      }
+
+      int stringTotalLength = stringHeapLength + stringListLength;
+      if (stringHeapLength == 0 && stringListLength > 0) {
+        // nothing from stringHeap
+        // add 1 for the null at the beginning
+        stringTotalLength += 1;
+      }
+      dos.writeInt(stringTotalLength);
+
+      // write the data in the stringheap, if there is any
+      if (stringTotalLength > 0) {
+        if (shdh.charHeapPos > 0) {
+          dos.writeChars(String.valueOf(shdh.charHeap, 0, shdh.charHeapPos));
+        } else {
+          // no stringheap data
+          // if there is data in the string lists, write a leading 0
+          if (stringListLength > 0) {
+            dos.writeChar(0);
+          }
+        }
+
+        // word alignment
+        if (stringTotalLength % 2 != 0) {
+          dos.writeChar(0);
+        }
+      }
+
+      // write out the string ref heap
+      // each reference consist of a offset into stringheap and a length
+      int refheapsz = ((shdh.refHeap.length - StringHeapDeserializationHelper.FIRST_CELL_REF) / StringHeapDeserializationHelper.REF_HEAP_CELL_SIZE) * 2;
+      refheapsz++;
+      dos.writeInt(refheapsz);
+      dos.writeInt(0);
+      for (int i = StringHeapDeserializationHelper.FIRST_CELL_REF; i < shdh.refHeap.length; i += 3) {
+        dos.writeInt(shdh.refHeap[i + StringHeapDeserializationHelper.CHAR_HEAP_POINTER_OFFSET]);
+        dos.writeInt(shdh.refHeap[i + StringHeapDeserializationHelper.CHAR_HEAP_STRLEN_OFFSET]);
+      }
+
+      //output modified FS Heap cells
+      int[] fsHeapModifiedAddrs = cas.getModifiedFSHeapAddrs().toArray();
+      dos.writeInt(fsHeapModifiedAddrs.length);  //num modified
+      for (int i=0; i < fsHeapModifiedAddrs.length; i++) {
+    	  dos.writeInt(fsHeapModifiedAddrs[i]);
+    	  dos.writeInt(cas.getHeapValue(fsHeapModifiedAddrs[i]));
+      }
+      
+      // output the index FSs
+      dos.writeInt(this.fsIndex.length);
+      for (int i = 0; i < this.fsIndex.length; i++) {
+        dos.writeInt(this.fsIndex[i]);
+      }
+
+      // 8bit heap new
+      int byteheapsz = cas.getByteHeap().getSize() - mark.nextByteHeapAddr;
+      dos.writeInt(byteheapsz);
+      for (int i = mark.nextByteHeapAddr; i < cas.getByteHeap().getSize(); i++) {
+        dos.writeByte(cas.getByteHeap().heap[i]);
+      }
+
+      // word alignment
+      int align = (4 - (byteheapsz % 4)) % 4;
+      for (int i = 0; i < align; i++) {
+        dos.writeByte(0);
+      }
+
+      // 16bit heap new
+      int shortheapsz = cas.getShortHeap().getSize() - mark.nextShortHeapAddr;
+      dos.writeInt(shortheapsz);
+      for (int i = mark.nextShortHeapAddr; i < cas.getShortHeap().getSize(); i++) {
+        dos.writeShort(cas.getShortHeap().heap[i]);
+      }
+
+      // word alignment
+      if (shortheapsz % 2 != 0) {
+        dos.writeShort(0);
+      }
+
+      // 64bit heap new 
+      int longheapsz = cas.getLongHeap().getSize() - mark.nextLongHeapAddr;
+      dos.writeInt(longheapsz);
+      for (int i = mark.nextLongHeapAddr; i < cas.getLongHeap().getSize(); i++) {
+        dos.writeLong(cas.getLongHeap().heap[i]);
+      }
+      
+      // 8 bit heap modified cells
+      int[] byteHeapModifiedAddrs = cas.getModifiedByteHeapAddrs().toArray();
+      byte[] byteValues = new byte[byteHeapModifiedAddrs.length];
+      dos.writeInt(byteHeapModifiedAddrs.length);
+      for (int i=0; i < byteHeapModifiedAddrs.length; i++) {
+    	dos.writeInt(byteHeapModifiedAddrs[i]);
+    	byteValues[i] = cas.getByteHeap().getHeapValue(byteHeapModifiedAddrs[i]);
+      }
+      for (int i=0; i < byteValues.length; i++) {  
+    	  dos.writeByte(cas.getByteHeap().getHeapValue(byteHeapModifiedAddrs[i]));
+	  }
+      
+      // word alignment
+      align = (4 - (byteheapsz % 4)) % 4;
+      for (int i = 0; i < align; i++) {
+        dos.writeByte(0);
+      }
+      
+      // 16 bit heap modified cells
+      int[] shortHeapModifiedAddrs = cas.getModifiedShortHeapAddrs().toArray();
+      short[] shortValues = new short[shortHeapModifiedAddrs.length];
+      dos.writeInt(shortHeapModifiedAddrs.length);
+      for (int i=0; i < shortHeapModifiedAddrs.length; i++) {
+    	dos.writeShort(shortHeapModifiedAddrs[i]);
+    	shortValues[i] = cas.getShortHeap().getHeapValue(shortHeapModifiedAddrs[i]);
+      }
+      for (int i=0; i < shortValues.length; i++) {  
+    	  dos.writeShort(cas.getShortHeap().getHeapValue(shortHeapModifiedAddrs[i]));
+	  }
+      
+      // word alignment
+      if (shortheapsz % 2 != 0) {
+        dos.writeShort(0);
+      }
+      
+      // 64 bit heap modified cells
+      int[] longHeapModifiedAddrs = cas.getModifiedShortHeapAddrs().toArray();
+      long[] longValues = new long[longHeapModifiedAddrs.length];
+      dos.writeInt(longHeapModifiedAddrs.length);
+      for (int i=0; i < longHeapModifiedAddrs.length; i++) {
+    	dos.writeShort(longHeapModifiedAddrs[i]);
+    	longValues[i] = cas.getLongHeap().getHeapValue(longHeapModifiedAddrs[i]);
+      }
+      for (int i=0; i < longValues.length; i++) {  
+    	  dos.writeLong(cas.getLongHeap().getHeapValue(longHeapModifiedAddrs[i]));
+	  }
+      
+    } catch (IOException e) {
+      CASRuntimeException exception = new CASRuntimeException(
+          CASRuntimeException.BLOB_SERIALIZATION, new String[] { e.getMessage() });
+      throw exception;
+    }
+
+  }
+
   /**
    * Method stringArrayListToArray.
    * 

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Heap.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Heap.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Heap.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Heap.java Mon Oct 20 07:22:11 2008
@@ -249,5 +249,10 @@
   public int getNextId() {
 	  return pos;
   }
-	  
+  
+  public void grow(int len) {
+	while ((this.pos + len) >= this.max) {
+	  grow();
+	}
+  }	  
 }

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/MarkerImpl.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/MarkerImpl.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/MarkerImpl.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/MarkerImpl.java Mon Oct 20 07:22:11 2008
@@ -25,11 +25,22 @@
 
 public class MarkerImpl implements Marker {
 	
-  private int nextFSId;
+  protected int nextFSId;    //next FS addr
+  protected int nextStringHeapAddr; 
+  protected int nextByteHeapAddr;
+  protected int nextShortHeapAddr;
+  protected int nextLongHeapAddr;
+  
   CASImpl cas;
 
-  MarkerImpl(int nextPos, CASImpl cas) {
-    this.nextFSId = nextPos;
+  MarkerImpl(int nextFSAddr, int nextStringHeapAddr, 
+		     int nextByteHeapAddr, int nextShortHeapAddr, int nextLongHeapAddr, 
+		     CASImpl cas) {
+    this.nextFSId = nextFSAddr;
+    this.nextStringHeapAddr = nextStringHeapAddr;
+    this.nextByteHeapAddr = nextByteHeapAddr;
+    this.nextShortHeapAddr = nextShortHeapAddr;
+    this.nextLongHeapAddr = nextLongHeapAddr;
     this.cas = cas;
   }
 

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Serialization.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Serialization.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Serialization.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/Serialization.java Mon Oct 20 07:22:11 2008
@@ -23,6 +23,7 @@
 import java.io.OutputStream;
 
 import org.apache.uima.cas.CAS;
+import org.apache.uima.cas.Marker;
 import org.apache.uima.cas.admin.CASMgr;
 
 public class Serialization {
@@ -77,4 +78,16 @@
     ((CASImpl) cas).reinit(istream);
   }
 
+  /**
+   * Serializes CAS data added or modified after the tracking Marker was created and writes it
+   * to the output stream in Delta CAS format
+   * @param cas
+   * @param ostream
+   * @param mark
+   */
+  public static void serializeCAS(CAS cas, OutputStream ostream, Marker mark) {
+	    CASSerializer ser = new CASSerializer();
+	    ser.addCAS((CASImpl) cas, ostream, mark);
+  }
+
 }

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/StringHeap.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/StringHeap.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/StringHeap.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/StringHeap.java Mon Oct 20 07:22:11 2008
@@ -48,8 +48,10 @@
    * 
    * @param shdh Serialization helper datastructure.
    */
-  final void reinit(StringHeapDeserializationHelper shdh) {
-    initMemory();
+  final void reinit(StringHeapDeserializationHelper shdh, boolean delta) {
+	if (!delta) {
+      initMemory();
+	}
     int stringOffset;
     int stringLength;
     // Simply iterate over the ref heap and add one string after another.  The references come out
@@ -96,6 +98,44 @@
     assert (charCount == shdh.charHeap.length);
     return shdh;
   }
+  
+  StringHeapDeserializationHelper serialize(int startPos) {
+    StringHeapDeserializationHelper shdh = new StringHeapDeserializationHelper();
+	// Ref heap is 3 times the size of the string list.
+	shdh.refHeap = new int[(this.stringList.size() - startPos + 1)
+			* StringHeapDeserializationHelper.REF_HEAP_CELL_SIZE];
+	shdh.refHeapPos = shdh.refHeap.length;
+	// Compute required size of character heap.
+	int charHeapSize = 0;   
+	for (int i = startPos; i < this.stringList.size(); i++) {
+		String s = this.stringList.get(i);
+		if (s != null) {
+			charHeapSize += s.length();
+		}
+	}
+	shdh.charHeap = new char[charHeapSize];
+	shdh.charHeapPos = shdh.charHeap.length;
+
+	int charCount = 0;
+	// Now write out the actual data
+	int r = 1;
+	for (int i = startPos; i < this.stringList.size(); i++) {
+		String s = this.stringList.get(i);
+		int refHeapOffset = r
+				* StringHeapDeserializationHelper.REF_HEAP_CELL_SIZE;
+		shdh.refHeap[refHeapOffset
+				+ StringHeapDeserializationHelper.CHAR_HEAP_POINTER_OFFSET] = charCount;
+		shdh.refHeap[refHeapOffset
+				+ StringHeapDeserializationHelper.CHAR_HEAP_STRLEN_OFFSET] = s
+				.length();
+		System.arraycopy(s.toCharArray(), 0, shdh.charHeap, charCount, s
+				.length());
+		charCount += s.length();
+		r++;
+	}
+	assert (charCount == shdh.charHeap.length);
+	return shdh;
+  }
 
   // Reset the string heap (called on CAS reset).
   final void reset() {
@@ -161,5 +201,9 @@
   final int getLargestStringCode() {
     return this.stringList.size() - 1;
   }
-
+  
+  final int getSize() {
+	  return this.stringList.size();
+  }
+  
 }

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/XmiCasSerializer.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/XmiCasSerializer.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/XmiCasSerializer.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/cas/impl/XmiCasSerializer.java Mon Oct 20 07:22:11 2008
@@ -73,6 +73,11 @@
   public static final int TYPE_CLASS_STRINGLIST = 103;
 
   public static final int TYPE_CLASS_FSLIST = 104;
+  
+  private static final char [] URIPFX = new char[] {'h','t','t','p',':','/','/','/'};
+  
+  private static final char [] URISFX = new char[] {'.','e','c','o','r','e'};
+
 
   // number of children of current element
   private int numChildren;
@@ -144,9 +149,12 @@
 
     // each type
 
-    private Map nsUriToPrefixMap = new HashMap();
-
-    private Set nsPrefixesUsed = new HashSet();
+    private Map<String, String> nsUriToPrefixMap = new HashMap<String, String>();
+    
+    // lives just for one serialize call
+    private Map<String, String> uniqueStrings = new HashMap<String, String>();
+    
+    private Set<String> nsPrefixesUsed = new HashSet<String>();
     
     /**
      * Used to tell if a FS was created before or after mark.
@@ -292,7 +300,7 @@
       if (sofaXmiId != null && sofaXmiId.length() > 0) {
         addAttribute(workAttrs, "sofa", sofaXmiId);
       }
-      StringBuffer membersString = new StringBuffer();
+      StringBuilder membersString = new StringBuilder();
       for (int i = 0; i < members.length; i++) {
         String xmiId = getXmiId(members[i]);
         if (xmiId != null) // to catch filtered FS
@@ -324,7 +332,7 @@
         if (sofaXmiId != null && sofaXmiId.length() > 0) {
           addAttribute(workAttrs, "sofa", sofaXmiId);
         }
-        StringBuffer addedString = new StringBuffer();
+        StringBuilder addedString = new StringBuilder();
         for (int i = 0; i < added.length; i++) {
           String xmiId = getXmiId(added[i]);
           if (xmiId != null) // to catch filtered FS
@@ -337,7 +345,7 @@
           addAttribute(workAttrs, "added_members", addedString.substring(0, addedString.length() - 1));
         }
         
-        StringBuffer deletedString = new StringBuffer();
+        StringBuilder deletedString = new StringBuilder();
         for (int i = 0; i < deleted.length; i++) {
           String xmiId = getXmiId(deleted[i]);
           if (xmiId != null) // to catch filtered FS
@@ -350,7 +358,7 @@
           addAttribute(workAttrs, "deleted_members", deletedString.substring(0, deletedString.length() - 1));
         }
         
-        StringBuffer reindexedString = new StringBuffer();
+        StringBuilder reindexedString = new StringBuilder();
         for (int i = 0; i < reindexed.length; i++) {
           String xmiId = getXmiId(reindexed[i]);
           if (xmiId != null) // to catch filtered FS
@@ -399,7 +407,7 @@
         workAttrs.addAttribute(XMLNS_NS_URI, "xsi", "xmlns:xsi", "CDATA", XSI_NS_URI);
 
         // write xsi:schemaLocation attributaiton
-        StringBuffer buf = new StringBuffer();
+        StringBuilder buf = new StringBuilder();
         it = nsUriToSchemaLocationMap.entrySet().iterator();
         while (it.hasNext()) {
           Map.Entry entry = (Map.Entry) it.next();
@@ -1003,7 +1011,7 @@
         return null;
       }
 
-      StringBuffer buf = new StringBuffer();
+      StringBuilder buf = new StringBuilder();
       final int size = cas.ll_getArraySize(addr);
       if (size > 0 && !arrayAndListFSs.put(addr, addr)) {
         reportWarning("Warning: multiple references to an array.  Reference identity will not be preserved in XMI.");
@@ -1117,7 +1125,7 @@
       if (addr == CASImpl.NULL) {
         return null;
       }
-      StringBuffer buf = new StringBuffer();
+      StringBuilder buf = new StringBuilder();
       String[] array = new String[0];
       switch (arrayType) {
         case TYPE_CLASS_INTLIST:
@@ -1206,7 +1214,7 @@
         // this also populats the nsUriToPrefix map
       }
     }
-
+    
     /**
      * Converts a UIMA-style dotted type name to the element name that should be used in the XMI
      * serialization. The XMI element name consists of three parts - the Namespace URI, the Local
@@ -1218,25 +1226,37 @@
      */
     private XmlElementName uimaTypeName2XmiElementName(String uimaTypeName) {
       // split uima type name into namespace and short name
-      String namespace, shortName, nsUri;
-      int lastDotIndex = uimaTypeName.lastIndexOf('.');
+      String shortName, nsUri;
+      final int lastDotIndex = uimaTypeName.lastIndexOf('.');
       if (lastDotIndex == -1) // no namespace
       {
-        namespace = null;
+//        namespace = null;
         shortName = uimaTypeName;
         nsUri = DEFAULT_NAMESPACE_URI;
       } else {
-        namespace = uimaTypeName.substring(0, lastDotIndex);
+//        namespace = uimaTypeName.substring(0, lastDotIndex);
         shortName = uimaTypeName.substring(lastDotIndex + 1);
-        nsUri = "http:///" + namespace.replace('.', '/') + ".ecore";
+        char[] sb = new char[lastDotIndex + 14];
+        System.arraycopy(URIPFX, 0, sb, 0, URIPFX.length);
+        int i = 0;
+        for (; i < lastDotIndex; i++) {
+          char c = uimaTypeName.charAt(i);
+          sb[URIPFX.length + i] = ( c == '.') ? '/' : c;
+        }
+        System.arraycopy(URISFX, 0, sb, URIPFX.length + i, URISFX.length);
+        nsUri = getUniqueString(new String(sb));
+        
+//        nsUri = "http:///" + namespace.replace('.', '/') + ".ecore"; 
       }
+      // convert short name to shared string, without interning, reduce GCs
+      shortName = getUniqueString(shortName);
 
       // determine what namespace prefix to use
       String prefix = (String) nsUriToPrefixMap.get(nsUri);
       if (prefix == null) {
-        if (namespace != null) {
-          int secondLastDotIndex = namespace.lastIndexOf('.');
-          prefix = namespace.substring(secondLastDotIndex + 1);
+        if (lastDotIndex != -1) { // have namespace 
+          int secondLastDotIndex = uimaTypeName.lastIndexOf('.', lastDotIndex-1);
+          prefix = uimaTypeName.substring(secondLastDotIndex + 1, lastDotIndex);
         } else {
           prefix = "noNamespace";
         }
@@ -1253,7 +1273,19 @@
         nsPrefixesUsed.add(prefix);
       }
 
-      return new XmlElementName(nsUri, shortName, prefix + ':' + shortName);
+      return new XmlElementName(nsUri, shortName, getUniqueString(prefix + ':' + shortName));
+    }
+
+    /** 
+     *  convert to shared string, without interning, reduce GCs
+     */
+    private String getUniqueString(String s) { 
+      String u = uniqueStrings.get(s);
+      if (null == u) {
+        u = s;
+        uniqueStrings.put(s, s);
+      }
+      return u;
     }
     
     /**

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/util/CasPool.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/util/CasPool.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/util/CasPool.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/main/java/org/apache/uima/util/CasPool.java Mon Oct 20 07:22:11 2008
@@ -21,7 +21,6 @@
 
 import java.util.ArrayList;
 import java.util.Collection;
-import java.util.Date;
 import java.util.Properties;
 import java.util.Vector;
 
@@ -251,14 +250,16 @@
    *         timeout period.
    */
   public synchronized CAS getCas(long aTimeout) {
-    long startTime = new Date().getTime();
+//    long startTime = new Date().getTime();
+    long startTime = System.currentTimeMillis();
     CAS cas;
     while ((cas = getCas()) == null) {
       try {
         wait(aTimeout);
       } catch (InterruptedException e) {
       }
-      if (aTimeout > 0 && (new Date().getTime() - startTime) >= aTimeout) {
+//    if (aTimeout > 0 && (new Date().getTime() - startTime) >= aTimeout) {
+    if (aTimeout > 0 && (System.currentTimeMillis() - startTime) >= aTimeout) {
         // Timeout has expired
         return null;
       }

Modified: incubator/uima/uimaj/trunk/uimaj-core/src/test/java/org/apache/uima/cas/test/SerializationReinitTest.java
URL: http://svn.apache.org/viewvc/incubator/uima/uimaj/trunk/uimaj-core/src/test/java/org/apache/uima/cas/test/SerializationReinitTest.java?rev=706304&r1=706303&r2=706304&view=diff
==============================================================================
--- incubator/uima/uimaj/trunk/uimaj-core/src/test/java/org/apache/uima/cas/test/SerializationReinitTest.java (original)
+++ incubator/uima/uimaj/trunk/uimaj-core/src/test/java/org/apache/uima/cas/test/SerializationReinitTest.java Mon Oct 20 07:22:11 2008
@@ -29,8 +29,10 @@
 
 import junit.framework.TestCase;
 
+import org.apache.uima.UIMAFramework;
 import org.apache.uima.cas.ArrayFS;
 import org.apache.uima.cas.ByteArrayFS;
+import org.apache.uima.cas.Marker;
 import org.apache.uima.cas.ShortArrayFS;
 import org.apache.uima.cas.CAS;
 import org.apache.uima.cas.CASException;
@@ -39,6 +41,7 @@
 import org.apache.uima.cas.FSIterator;
 import org.apache.uima.cas.Feature;
 import org.apache.uima.cas.FeatureStructure;
+import org.apache.uima.cas.StringArrayFS;
 import org.apache.uima.cas.Type;
 import org.apache.uima.cas.TypeSystem;
 import org.apache.uima.cas.admin.CASAdminException;
@@ -50,12 +53,16 @@
 import org.apache.uima.cas.impl.LowLevelCAS;
 import org.apache.uima.cas.impl.Serialization;
 import org.apache.uima.cas.text.AnnotationFS;
+import org.apache.uima.cas_data.impl.CasComparer;
 import org.apache.uima.internal.util.TextStringTokenizer;
 import org.apache.uima.resource.ResourceInitializationException;
+import org.apache.uima.resource.metadata.FsIndexDescription;
 import org.apache.uima.resource.metadata.TypeSystemDescription;
+import org.apache.uima.resource.metadata.impl.TypePriorities_impl;
 import org.apache.uima.test.junit_extension.JUnitExtension;
 import org.apache.uima.util.CasCreationUtils;
 import org.apache.uima.util.FileUtils;
+import org.apache.uima.util.XMLInputSource;
 
 /**
  * Class comment for TokenizerTest.java goes here.
@@ -133,6 +140,10 @@
   private Feature theShortArrayFeature;
   
   private Feature theLongFeature;
+  
+  private FsIndexDescription[] indexes;
+
+  private TypeSystemDescription typeSystem;
 
 
   public SerializationReinitTest(String arg) {
@@ -166,6 +177,15 @@
     theShortFeature = ts.getFeatureByFullName(OSTR_TYPE + TypeSystem.FEATURE_SEPARATOR + OSHORT_TYPE_FEAT);
     theShortArrayFeature = ts.getFeatureByFullName(OSTR_TYPE + TypeSystem.FEATURE_SEPARATOR + OSHORTA_TYPE_FEAT);
     theLongFeature = ts.getFeatureByFullName(OSTR_TYPE + TypeSystem.FEATURE_SEPARATOR + OLONG_TYPE_FEAT);
+ 
+  
+    File typeSystemFile = JUnitExtension.getFile("ExampleCas/testTypeSystem.xml");
+    File indexesFile = JUnitExtension.getFile("ExampleCas/testIndexes.xml");
+
+    typeSystem = UIMAFramework.getXMLParser().parseTypeSystemDescription(
+                new XMLInputSource(typeSystemFile));
+    indexes = UIMAFramework.getXMLParser().parseFsIndexCollection(new XMLInputSource(indexesFile))
+                .getFsIndexes();
   }
 
   public void tearDown() {
@@ -181,6 +201,8 @@
     endFeature = null;
     sentenceType = null;
     strSub1 = null;
+    indexes = null;
+    typeSystem = null;
   }
 
   // Initialize the first CAS.
@@ -684,6 +706,213 @@
     }  
   }
 
+  public void testDeltaBlobSerialization() throws Exception {
+   try {
+      CAS cas1 = CasCreationUtils.createCas(typeSystem, new TypePriorities_impl(),
+              indexes);
+      CAS cas2 = CasCreationUtils.createCas(typeSystem, new TypePriorities_impl(),
+              indexes);
+      CAS cas3 = CasCreationUtils.createCas(typeSystem, new TypePriorities_impl(),
+              indexes);
+      
+      Type personType = cas1.getTypeSystem().getType(
+      		"org.apache.uima.testTypeSystem.Person");
+      Feature componentIdFeat = personType.getFeatureByBaseName("componentId");
+      Feature confidenceFeat = personType.getFeatureByBaseName("confidence");
+      Type orgType = cas1.getTypeSystem().getType(
+			"org.apache.uima.testTypeSystem.Organization");
+      Type ownerType = cas1.getTypeSystem().getType(
+      						"org.apache.uima.testTypeSystem.Owner");
+      Type entityAnnotType = cas1.getTypeSystem().getType(
+		"org.apache.uima.testTypeSystem.EntityAnnotation");
+      Feature mentionTypeFeat = entityAnnotType.getFeatureByBaseName("mentionType");
+      Feature argsFeat = ownerType.getFeatureByBaseName("relationArgs");
+      Type relArgsType = cas1.getTypeSystem().getType(
+      						"org.apache.uima.testTypeSystem.BinaryRelationArgs");
+      Feature domainFeat = relArgsType.getFeatureByBaseName("domainValue");
+      Feature rangeFeat = relArgsType.getFeatureByBaseName("rangeValue");
+      
+      Type entityType = cas1.getTypeSystem().getType("org.apache.uima.testTypeSystem.Entity");
+      Feature classesFeat = entityType.getFeatureByBaseName("classes");
+      Feature linksFeat = entityType.getFeatureByBaseName("links");
+      Feature canonicalFormFeat = entityType.getFeatureByBaseName("canonicalForm");
+      
+      Type nonEmptyFsListType = cas1.getTypeSystem().getType(CAS.TYPE_NAME_NON_EMPTY_FS_LIST);
+      Type emptyFsListType = cas1.getTypeSystem().getType(CAS.TYPE_NAME_EMPTY_FS_LIST);
+      Feature headFeat = nonEmptyFsListType.getFeatureByBaseName("head");
+      Feature tailFeat = nonEmptyFsListType.getFeatureByBaseName("tail");
+      
+      //cas1
+      //initial set of feature structures 
+      // set document text for the initial view and create Annotations
+      cas1.setDocumentText("This is a test document in the initial view");
+      AnnotationFS anAnnot1 = cas1.createAnnotation(cas1.getAnnotationType(), 0, 4);
+      cas1.getIndexRepository().addFS(anAnnot1);
+      AnnotationFS anAnnot2 = cas1.createAnnotation(cas1.getAnnotationType(), 5, 6);
+      cas1.getIndexRepository().addFS(anAnnot2);
+      AnnotationFS anAnnot3 = cas1.createAnnotation(cas1.getAnnotationType(), 8, 13);
+      cas1.getIndexRepository().addFS(anAnnot3);
+      AnnotationFS anAnnot4 = cas1.createAnnotation(cas1.getAnnotationType(), 15, 30);
+      cas1.getIndexRepository().addFS(anAnnot4);
+      FSIndex tIndex = cas1.getAnnotationIndex();
+      assertTrue(tIndex.size() == 5); //doc annot plus 4 annots
+      
+      FeatureStructure entityFS = cas1.createFS(entityType);
+      cas1.getIndexRepository().addFS(entityFS);
+      
+      StringArrayFS strArrayFS = cas1.createStringArrayFS(5);
+      strArrayFS.set(0, "class1");
+      entityFS.setFeatureValue(classesFeat, strArrayFS);
+      
+      //create listFS and set the link feature
+      FeatureStructure emptyNode = cas1.createFS(emptyFsListType);
+      FeatureStructure secondNode = cas1.createFS(nonEmptyFsListType);
+      secondNode.setFeatureValue(headFeat, anAnnot2);
+      secondNode.setFeatureValue(tailFeat, emptyNode);
+      FeatureStructure firstNode = cas1.createFS(nonEmptyFsListType);
+      firstNode.setFeatureValue(headFeat, anAnnot1);
+      firstNode.setFeatureValue(tailFeat, secondNode);
+      entityFS.setFeatureValue(linksFeat, firstNode);
+      
+      // create a view w/o setting document text
+      CAS view1 = cas1.createView("View1");
+      
+      // create another view 
+      CAS preexistingView = cas1.createView("preexistingView");
+      String preexistingViewText = "John Smith blah blah blah";
+      preexistingView.setDocumentText(preexistingViewText);
+      AnnotationFS person1Annot = createPersonAnnot(preexistingView, 0, 10);
+      person1Annot.setStringValue(componentIdFeat, "deltacas1");
+      AnnotationFS person2Annot = createPersonAnnot(preexistingView, 0, 5);
+      AnnotationFS orgAnnot = preexistingView.createAnnotation(orgType, 16, 24);
+      preexistingView.addFsToIndexes(orgAnnot);
+      
+      AnnotationFS ownerAnnot = preexistingView.createAnnotation(ownerType, 0, 24);
+      preexistingView.addFsToIndexes(ownerAnnot);
+      FeatureStructure relArgs = cas1.createFS(relArgsType);
+      relArgs.setFeatureValue(domainFeat, person1Annot);
+      ownerAnnot.setFeatureValue(argsFeat, relArgs);
+      
+      //serialize complete 
+      ByteArrayOutputStream fos = new ByteArrayOutputStream();
+      Serialization.serializeCAS(cas1, fos);
+
+      //deserialize into cas2
+      ByteArrayInputStream fis = new ByteArrayInputStream(fos.toByteArray());
+      Serialization.deserializeCAS(cas2, fis);
+      CasComparer.assertEquals(cas1, cas2);
+ 
+      //=======================================================================
+      //create Marker, add/modify fs and serialize in delta xmi format.
+      Marker marker = cas2.createMarker();
+      FSIndex cas2tIndex = cas2.getAnnotationIndex();
+      CAS cas2preexistingView = cas2.getView("preexistingView");
+      FSIndex cas2personIndex = cas2preexistingView.getAnnotationIndex(personType);
+      FSIndex cas2orgIndex = cas2preexistingView.getAnnotationIndex(orgType);
+      FSIndex cas2ownerIndex = cas2preexistingView.getAnnotationIndex(ownerType);
+      
+      // create an annotation and add to index
+      AnnotationFS cas2anAnnot5 = cas2.createAnnotation(cas2.getAnnotationType(), 6, 8);
+      cas2.getIndexRepository().addFS(cas2anAnnot5);
+      assertTrue(cas2tIndex.size() == 6); // prev annots and this new one
+      
+      // set document text of View1
+      CAS cas2view1 = cas2.getView("View1");
+      cas2view1.setDocumentText("This is the View1 document.");
+      //create an annotation in View1
+      AnnotationFS cas2view1Annot = cas2view1.createAnnotation(cas2.getAnnotationType(), 1, 5);
+      cas2view1.getIndexRepository().addFS(cas2view1Annot);
+      FSIndex cas2view1Index = cas2view1.getAnnotationIndex();
+      assertTrue(cas2view1Index.size() == 2); //document annot and this annot
+     
+      //modify an existing annotation
+      Iterator tIndexIter = cas2tIndex.iterator();
+      AnnotationFS docAnnot = (AnnotationFS) tIndexIter.next(); //doc annot
+      AnnotationFS modAnnot1 = (AnnotationFS) tIndexIter.next();
+      AnnotationFS delAnnot = (AnnotationFS)  tIndexIter.next();
+      
+      //modify language feature
+      Feature languageF = cas2.getDocumentAnnotation().getType().getFeatureByBaseName(CAS.FEATURE_BASE_NAME_LANGUAGE);
+      docAnnot.setStringValue(languageF, "en");
+     
+      //index update - reindex
+      cas2.getIndexRepository().removeFS(modAnnot1);
+      Feature endF = cas2.getAnnotationType().getFeatureByBaseName(CAS.FEATURE_BASE_NAME_END);
+      modAnnot1.setIntValue(endF, 4);
+      cas2.getIndexRepository().addFS(modAnnot1);
+      //index update - remove annotation from index 
+      cas2.getIndexRepository().removeFS(delAnnot);
+  
+      //modify FS - string feature and FS feature.
+      Iterator personIter = cas2personIndex.iterator();     
+      AnnotationFS cas2person1 = (AnnotationFS) personIter.next();
+      AnnotationFS cas2person2 = (AnnotationFS) personIter.next();
+      
+      cas2person1.setFloatValue(confidenceFeat, (float) 99.99);
+      cas2person1.setStringValue(mentionTypeFeat, "FULLNAME");
+      
+      cas2person2.setStringValue(componentIdFeat, "delataCas2");
+      cas2person2.setStringValue(mentionTypeFeat, "FIRSTNAME");
+      
+      Iterator orgIter = cas2orgIndex.iterator();
+      AnnotationFS cas2orgAnnot = (AnnotationFS) orgIter.next();
+      cas2orgAnnot.setStringValue(mentionTypeFeat, "ORGNAME");
+      
+      //modify FS feature
+      Iterator ownerIter = cas2ownerIndex.iterator();
+      AnnotationFS cas2ownerAnnot = (AnnotationFS) ownerIter.next();
+      FeatureStructure cas2relArgs = cas2ownerAnnot.getFeatureValue(argsFeat);
+      cas2relArgs.setFeatureValue(rangeFeat, cas2orgAnnot);
+     
+    //Test modification of a nonshared multivalued feature.
+      //This should serialize the encompassing FS.
+      Iterator iter = cas2.getIndexRepository().getIndex("testEntityIndex").iterator();
+      FeatureStructure cas2EntityFS = (FeatureStructure) iter.next();
+      StringArrayFS cas2strarrayFS = (StringArrayFS) cas2EntityFS.getFeatureValue(classesFeat);
+      cas2strarrayFS.set(1, "class2");
+      cas2strarrayFS.set(2, "class3");
+      cas2strarrayFS.set(3, "class4");
+      cas2strarrayFS.set(4, "class5");
+     
+      //add to FSList 
+      FeatureStructure cas2linksFS = cas2EntityFS.getFeatureValue(linksFeat);
+      FeatureStructure cas2secondNode = cas2linksFS.getFeatureValue(tailFeat);
+      FeatureStructure cas2emptyNode = cas2secondNode.getFeatureValue(tailFeat);
+      FeatureStructure cas2thirdNode = cas2.createFS(nonEmptyFsListType);
+      cas2thirdNode.setFeatureValue(headFeat, cas2anAnnot5);
+      cas2thirdNode.setFeatureValue(tailFeat, cas2emptyNode);
+      cas2secondNode.setFeatureValue(tailFeat, cas2thirdNode);
+      
+      // serialize cas2 in delta format 
+      ByteArrayOutputStream fosDelta = new ByteArrayOutputStream();
+      Serialization.serializeCAS(cas2, fosDelta, marker);
+      
+      //======================================================================
+      //deserialize delta xmi into cas1
+      ByteArrayInputStream fisDelta = new ByteArrayInputStream(fosDelta.toByteArray());
+      Serialization.deserializeCAS(cas1, fisDelta);
+      
+      //======================================================================
+      //serialize complete cas and deserialize into cas3 and compare with cas1.
+      ByteArrayOutputStream fosFull = new ByteArrayOutputStream();
+      Serialization.serializeCAS(cas2, fosFull);
+      ByteArrayInputStream fisFull = new ByteArrayInputStream(fosFull.toByteArray());
+      Serialization.deserializeCAS(cas3, fisFull);
+      CasComparer.assertEquals(cas1, cas3); 
+      //System.out.println("CAS1 " + serialize(cas1, new XmiSerializationSharedData()));
+      //System.out.println("CAS2 " + serialize(cas2, new XmiSerializationSharedData()));
+	      
+	} catch (Exception e) {
+	      JUnitExtension.handleException(e);
+	}
+  }
+  
+  private AnnotationFS createPersonAnnot(CAS cas, int begin, int end) {
+	Type personType = cas.getTypeSystem().getType("org.apache.uima.testTypeSystem.Person");
+	AnnotationFS person = cas.createAnnotation(personType, begin, end);
+	cas.addFsToIndexes(person);
+	return person;
+  }
   public static void main(String[] args) {
     junit.textui.TestRunner.run(SerializationReinitTest.class);
   }



Mime
View raw message