1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159
|
package uk.ac.bristol.star.cdf.record;
import java.io.IOException;
import uk.ac.bristol.star.cdf.DataType;
/**
* Abstract superclass for CDF Variable Descriptor Records.
* Two concrete subclasses exist for rVDRs and zVDRs.
*
* @author Mark Taylor
* @since 19 Jun 2013
*/
public abstract class VariableDescriptorRecord extends Record {
@CdfField @OffsetField public final long vdrNext;
@CdfField public final int dataType;
@CdfField public final int maxRec;
@CdfField @OffsetField public final long vxrHead;
@CdfField @OffsetField public final long vxrTail;
@CdfField public final int flags;
@CdfField public final int sRecords;
@CdfField public final int rfuB;
@CdfField public final int rfuC;
@CdfField public final int rfuF;
@CdfField public final int numElems;
@CdfField public final int num;
@CdfField @OffsetField public final long cprOrSprOffset;
@CdfField public final int blockingFactor;
@CdfField public final String name;
@CdfField public final int zNumDims;
@CdfField public final int[] zDimSizes;
@CdfField public final boolean[] dimVarys;
private final long padOffset_;
private final int padBytes_;
/**
* Constructor.
*
* @param plan basic record info
* @param abbrev abbreviated name for record type
* @param recordType record type code
* @param hasDims true iff the zNumDims and zDimSizes fields
* will be present
* @param nameLeng number of characters used for attribute names
*/
private VariableDescriptorRecord( RecordPlan plan, String abbrev,
int recordType, boolean hasDims,
int nameLeng )
throws IOException {
super( plan, abbrev, recordType );
Buf buf = plan.getBuf();
Pointer ptr = plan.createContentPointer();
this.vdrNext = buf.readOffset( ptr );
this.dataType = buf.readInt( ptr );
this.maxRec = buf.readInt( ptr );
this.vxrHead = buf.readOffset( ptr );
this.vxrTail = buf.readOffset( ptr );
this.flags = buf.readInt( ptr );
this.sRecords = buf.readInt( ptr );
this.rfuB = buf.readInt( ptr );
this.rfuC = buf.readInt( ptr );
this.rfuF = buf.readInt( ptr );
this.numElems = buf.readInt( ptr );
this.num = buf.readInt( ptr );
this.cprOrSprOffset = buf.readOffset( ptr );
this.blockingFactor = buf.readInt( ptr );
this.name = buf.readAsciiString( ptr, nameLeng );
if ( hasDims ) {
this.zNumDims = buf.readInt( ptr );
this.zDimSizes = readIntArray( buf, ptr, this.zNumDims );
}
else {
this.zNumDims = 0;
this.zDimSizes = null;
}
boolean hasPad = hasBit( this.flags, 1 );
padBytes_ = hasPad ? DataType.getDataType( this.dataType )
.getByteCount() * this.numElems
: 0;
final int ndim;
if ( hasDims ) {
ndim = this.zNumDims;
}
else {
// Work out the number of dimensions of an rVariable by subtracting
// the values of all the other fields from the record size.
// The more direct way would be by using the rNumDims field of
// the GDR, but we don't have access to that here.
long runningCount = plan.getReadCount( ptr );
long spareBytes = getRecordSize() - runningCount - padBytes_;
assert spareBytes == (int) spareBytes;
if ( spareBytes % 4 != 0 ) {
warnFormat( "rVDR DimVarys field non-integer size??" );
}
ndim = ( (int) spareBytes ) / 4;
}
int[] iDimVarys = readIntArray( buf, ptr, ndim );
this.dimVarys = new boolean[ ndim ];
for ( int i = 0; i < ndim; i++ ) {
this.dimVarys[ i ] = iDimVarys[ i ] != 0;
}
long padpos = ptr.getAndIncrement( padBytes_ );
padOffset_ = hasPad ? padpos : -1L;
checkEndRecord( ptr );
}
/**
* Returns the file offset at which this record's PadValue can be found.
* If there is no pad value, -1 is returned.
*
* @return pad file offset, or -1
*/
public long getPadValueOffset() {
return padOffset_;
}
/**
* Returns the number of bytes in the pad value.
* If there is no pad value, 0 is returned.
*
* @return pad value size in bytes
*/
public int getPadValueSize() {
return padBytes_;
}
/**
* Field data for CDF record of type rVariable Descriptor Record.
*/
public static class RVariant extends VariableDescriptorRecord {
/**
* Constructor.
*
* @param plan basic record info
* @param nameLeng number of characters used for attribute names
*/
public RVariant( RecordPlan plan, int nameLeng ) throws IOException {
super( plan, "rVDR", 3, false, nameLeng );
}
}
/**
* Field data for CDF record of type zVariable Descriptor Record.
*/
public static class ZVariant extends VariableDescriptorRecord {
/**
* Constructor.
*
* @param plan basic record info
* @param nameLeng number of characters used for attribute names
*/
public ZVariant( RecordPlan plan, int nameLeng ) throws IOException {
super( plan, "zVDR", 8, true, nameLeng );
}
}
}
|