classdef ucf < handle % Low-level utilities for UCF files. properties (Access = public) File % file name Type % file type Class % file class Endian % endianess CodeVersion % version of the simulation code UCFVersion % version of the data format ("unified container format") NumDataset % maximum number of datasets in this file (over all time steps) NumTimestep % number of time steps in this file FileSize % file size CreationTime % time of creation IOMode % file opened in read-only or read-write mode? IORank % rank of processor + col,row,pln Verbosity % verbose output? Debug % debug information? end properties (Access = private) % File info fileID fileBeg fileEnd typeID ioflag tarflag creationTimeUnix versionMajor versionMinor versionPatch versionFile % Step pointers and info posStep numSetPerStep timeStep % Write-mode isFileHeaderWritten isStepHeaderWritten % Current step information (should be resetable by resetCurrentStep()) currentStep currentStepPosHeader currentStepPosData currentStepSize currentStepTime currentStepNumSet % Current set information (should be resetable by resetCurrentSet()) currentSet currentSetPosHeader currentSetPosData currentSetSize currentSetDatatype currentSetDatatypeNumeric currentSetSizeof currentSetNumParams currentSetParams currentSetNumElements % Constants magicFile = int64(81985529216486895); magicStep = int64(11944304052957); magicSet = int64(240217520921210); nHeaderFile = 8; nHeaderStep = 4; nHeaderSet = 4; nByteHeaderFile = 8; nByteHeaderStep = 8; nByteHeaderSet = 8; nSetParamsField = 10; nSetParamsParticle = 16; factorMajor = 1000000000; factorMinor = 1000000; factorPatch = 1000; factorTypeIDClass = 1000; factorTypeIDKind = 10; typeIDmatlabField = 1999; typeIDmatlabParticle = 2999; scanBuffSize = 4096; end %% ------------------------------------------------------------------------%% %% CONSTRUCORS/DESTRUCTORS %% %% ------------------------------------------------------------------------%% methods(Access=public) function obj = ucf(varargin) % obj = ucf(varargin) % Default contructor % Input % ? verbosity verbose output? (default: false) % ? debug debug output? (default: false) par = inputParser; addOptional(par,'verbosity',0,@isnumeric); addOptional(par,'debug',0,@isnumeric); parse(par,varargin{:}); obj.resetPublicProperties(); obj.resetPrivateProperties(); obj.resetCurrentStep(); obj.resetCurrentSet(); obj.fileID = -1; obj.tarflag = false; obj.setVerbosity(par.Results.verbosity); obj.setDebug(par.Results.debug); end function delete(obj) % obj.delete() % Default destructor obj.close(); end end %% ------------------------------------------------------------------------%% %% INITIALIZATION METHODS %% %% ------------------------------------------------------------------------%% methods(Access=public) function open(obj,file) % obj.open(file) % Opens a file in read-only mode obj.File = file; % add filename as object property obj.IOMode = 'read'; % abstract IO mode obj.ioflag = 'r'; % internal IO mode obj.tarflag = false; % data is within a tar file? % Try to open the file obj.fileID = fopen(obj.File,obj.ioflag); if obj.fileID<0 error('Unable to open file: %s',obj.File); end obj.fileBeg = ftell(obj.fileID); fseek(obj.fileID,0,'eof'); obj.fileEnd = ftell(obj.fileID); fseek(obj.fileID,0,'bof'); obj.FileSize = obj.fileEnd-obj.fileBeg; % Read the file header obj.readHeaderFile() % Scan through file to get the basic structure (steps/sets) obj.timeStep = zeros(1,obj.scanBuffSize,'double'); obj.posStep = zeros(1,obj.scanBuffSize,'double'); obj.numSetPerStep = zeros(1,obj.scanBuffSize,'double'); istep = 0; while ftell(obj.fileID)obj.scanBuffSize warning('Buffer overflow detected: increase scanBuffSize.'); end obj.timeStep = obj.timeStep(1:nstep); obj.posStep = obj.posStep(1:nstep); obj.numSetPerStep = obj.numSetPerStep(1:nstep); % Set some internal variables obj.NumDataset = max(obj.numSetPerStep); obj.NumTimestep = nstep; obj.isFileHeaderWritten = true; obj.isStepHeaderWritten = true; end function edit(obj,file) % obj.edit(file) % Opens a file in read-write mode obj.File = file; % add filename as object property obj.IOMode = 'edit'; % abstract IO mode obj.ioflag = 'r+'; % internal IO mode obj.tarflag = false; % data is within a tar file? % Try to open the file obj.fileID = fopen(obj.File,obj.ioflag); if obj.fileID<0 error('Unable to open file: %s',obj.File); end % Read the file header obj.readHeaderFile() % Scan through file to get the basic structure (steps/sets) obj.timeStep = zeros(1,obj.scanBuffSize,'double'); obj.posStep = zeros(1,obj.scanBuffSize,'double'); obj.numSetPerStep = zeros(1,obj.scanBuffSize,'double'); istep = 0; while ftell(obj.fileID)obj.scanBuffSize warning('Buffer overflow detected: increase scanBuffSize.'); end obj.timeStep = obj.timeStep(1:nstep); obj.posStep = obj.posStep(1:nstep); obj.numSetPerStep = obj.numSetPerStep(1:nstep); % Set some internal variables obj.NumDataset = max(obj.numSetPerStep); obj.NumTimestep = nstep; obj.isFileHeaderWritten = true; obj.isStepHeaderWritten = true; end function create(obj,file,varargin) % obj.create(file,varargin) % Creates a new file and writes file header % Input % file file name/path % ? type file type {'field' (default),'particle'} % ? rank proc rank (default: [0,0,0,0]) % ? endian endianess {'n' (dafault),'a','l','s','b'} par = inputParser; addOptional(par,'type','field',@ischar); addOptional(par,'rank',[0,0,0,0],@(x)(isnumeric(x)&&numel(x)==4)); addOptional(par,'endian','n',@ischar); parse(par,varargin{:}); % obj.File = file; % add filename as object property obj.IOMode = 'create'; % abstract IO mode obj.ioflag = 'w+'; % internal IO mode obj.tarflag = false; % data is within a tar file? obj.isFileHeaderWritten = false; obj.isStepHeaderWritten = false; % Try to create the file obj.fileID = fopen(obj.File,obj.ioflag); if obj.fileID<0 error('Unable to create file: %s',obj.File); end % switch par.Results.type case 'field' obj.typeID = obj.typeIDmatlabField; obj.Class = 'field'; case 'particle' obj.typeID = obj.typeIDmatlabParticle; obj.Class = 'particle'; otherwise error('Unknown file type: %s',par.Results.type); end obj.IORank = par.Results.rank; obj.Endian = par.Results.endian; obj.versionMajor = 0; obj.versionMinor = 0; obj.versionPatch = 0; obj.versionFile = 1; obj.writeHeaderFile(); end function opentar(obj,ptr) % obj.opentar(ptr) % Opens a subfile from tar in read-only mode obj.File = 'tar-mode'; % Set generic file name obj.IOMode = 'read'; % abstract IO mode obj.ioflag = 'r'; % internal IO mode obj.tarflag = true; % data is within a tar file? % Set file ID to tar file ID obj.fileID = ptr(1); if obj.fileID<0 error('Unable to access file: %s',obj.File); end obj.fileBeg = ptr(2); obj.fileEnd = ptr(2)+ptr(3); obj.FileSize = ptr(3); % Read the file header obj.readHeaderFile() % Scan through file to get the basic structure (steps/sets) obj.timeStep = zeros(1,obj.scanBuffSize,'double'); obj.posStep = zeros(1,obj.scanBuffSize,'double'); obj.numSetPerStep = zeros(1,obj.scanBuffSize,'double'); istep = 0; while ftell(obj.fileID)obj.scanBuffSize warning('Buffer overflow detected: increase scanBuffSize.'); end obj.timeStep = obj.timeStep(1:nstep); obj.posStep = obj.posStep(1:nstep); obj.numSetPerStep = obj.numSetPerStep(1:nstep); % Set some internal variables obj.NumDataset = max(obj.numSetPerStep); obj.NumTimestep = nstep; obj.isFileHeaderWritten = true; obj.isStepHeaderWritten = true; end end %% ------------------------------------------------------------------------%% %% PUBLIC METHODS %% %% ------------------------------------------------------------------------%% methods(Access=public) function close(obj) % obj.close() % Closes a file obj.resetPublicProperties(); obj.resetPrivateProperties(); obj.resetCurrentStep(); obj.resetCurrentSet(); if obj.tarflag obj.tarflag = false; obj.fileID = -1; return; end if obj.fileID<0 return; end status = fclose(obj.fileID); if status<0 warning('Unable to close file (exit code: %d)',status); return; end obj.fileID = -1; end function [isType] = validateType(obj,type) switch type case 'grid' isType = (obj.typeID==0); case 'procgrid' isType = (obj.typeID==10); case 'field' isType = (floor(obj.typeID/obj.factorTypeIDClass)==1); case 'particle' isType = (floor(obj.typeID/obj.factorTypeIDClass)==2); case 'snapshot' isType = (mod(obj.typeID,obj.factorTypeIDKind)==0); case 'append' isType = (mod(obj.typeID,obj.factorTypeIDKind)==1); case {'uvwp','fluid'} isType = (obj.typeID==1000); case 'scalar' isType = (obj.typeID==1010); case 'matlab' isType = (mod(obj.typeID,obj.factorTypeIDKind)==9); otherwise error('Unknown type: %s',type); end end % ------------------------------------------------------------------------% % Read % % ------------------------------------------------------------------------% function [data,params] = readSet(obj,tstep,dset) % [data,params] = obj.readSet(tstep,dset) % Reads a raw dataset from file (no reshaping or parsing of parameters) % Input % tstep index of timestep to be read % dset index of dataset to be read % Output % data raw data with dim(1,nelements) % params raw parameters with dim(1,nparams) fseek(obj.fileID,obj.findSet(tstep,dset),'bof'); obj.readHeaderSet(); params = obj.currentSetParams; data = fread(obj.fileID,[1,obj.currentSetNumElements],... [obj.currentSetDatatype,'=>',obj.currentSetDatatype]); end function [params] = readParameters(obj,tstep,dset) % [data,params] = obj.readParameters(tstep,dset) % Reads a raw set of parameters without parsing. % Input % tstep index of timestep to be read % dset index of dataset to be read % Output % params raw parameters with dim(1,nparams) fseek(obj.fileID,obj.findSet(tstep,dset),'bof'); if obj.Debug fprintf('Skipped to position %d\n',ftell(obj.fileID)); end obj.readHeaderSet(); params = obj.currentSetParams; end % ------------------------------------------------------------------------% % Append % % ------------------------------------------------------------------------% function appendStep(obj,time) % [] = obj.appendStep(time) % Creates a new step at the end of opened file. % Input % time simulation time if ~obj.verifyWriteMode() error('File must be opened in create/edit mode.'); end % obj.resetCurrentStep(); obj.resetCurrentSet(); % fseek(obj.fileID,0,'eof'); obj.currentStep = obj.NumTimestep+1; obj.currentStepPosHeader = ftell(obj.fileID); obj.currentStepSize = 0; obj.currentStepTime = time; obj.currentStepNumSet = 0; obj.writeHeaderStep(); obj.currentStepPosData = ftell(obj.fileID); obj.currentSet = 0; % obj.NumTimestep = obj.currentStep; obj.posStep(obj.currentStep) = obj.currentStepPosData; obj.numSetPerStep(obj.currentStep) = obj.currentStepNumSet; obj.timeStep(obj.currentStep) = obj.currentStepTime; % if obj.Verbosity fprintf('Created timestep #%d with time = %f\n',obj.NumTimestep,obj.currentStepTime); end end function appendSet(obj,data,params) % [] = obj.appendSet(data,params) % Creates a new dataset at the end of opened file and writes data. % Input % data data to append % parameters dataset header parameters if ~obj.verifyWriteMode() error('File must be opened in create/edit mode.'); end % Evaluate datatype obj.currentSetDatatype = class(data); switch obj.currentSetDatatype case 'int32'; obj.currentSetDatatypeNumeric = 11; obj.currentSetSizeof = 4; case 'int64'; obj.currentSetDatatypeNumeric = 12; obj.currentSetSizeof = 8; case 'single'; obj.currentSetDatatypeNumeric = 21; obj.currentSetSizeof = 4; case 'double'; obj.currentSetDatatypeNumeric = 22; obj.currentSetSizeof = 8; otherwise error('Datatype not implemented: %s',obj.currentSetDatatype); end % Append a new set header fseek(obj.fileID,0,'eof'); obj.currentSet = obj.numSetPerStep(obj.currentStep)+1; obj.currentSetPosHeader = ftell(obj.fileID); obj.currentSetSize = numel(data)*obj.currentSetSizeof; switch obj.Class case 'field'; obj.currentSetNumParams = obj.nSetParamsField; case 'particle'; obj.currentSetNumParams = obj.nSetParamsParticle; otherwise; error('Invalid file class: %s',obj.Class); end obj.currentSetParams = zeros(1,obj.currentSetNumParams,'int64'); obj.currentSetParams(1:numel(params)) = params; obj.writeHeaderSet(); % Append actual data obj.currentSetPosData = ftell(obj.fileID); fwrite(obj.fileID,data(:),obj.currentSetDatatype,0,obj.Endian); % Rewrite step header obj.currentStepNumSet = obj.currentStepNumSet+1; obj.currentStepSize = obj.currentStepSize+... (4+obj.currentSetNumParams)*obj.nByteHeaderStep+... obj.currentSetSize; obj.writeHeaderStep(); % Update internal variables obj.numSetPerStep(obj.currentStep) = obj.currentSet; obj.NumDataset = max(obj.currentSet,obj.NumDataset); % Verbose output if obj.Verbosity fprintf('Created dataset %d at timestep #%d\n',obj.currentSet,obj.currentStep); end end function exchangeSet(obj,istep,iset,data) % [] = obj.exchangeSet(istep,iset,data) % Exchanges the data stored in dataset (istep,iset) with the data provided. % Input % data data, which replaces dataset (must be same size and type) if ~obj.verifyWriteMode() error('File must be opened in create/edit mode.'); end % Evaluate datatype and datasize dtype = class(data); switch dtype case 'int32'; dtypeNumeric = 11; dtypeSizeof = 4; case 'int64'; dtypeNumeric = 12; dtypeSizeof = 8; case 'single'; dtypeNumeric = 21; dtypeSizeof = 4; case 'double'; dtypeNumeric = 22; dtypeSizeof = 8; otherwise error('Datatype not implemented: %s',dtype); end dsize = numel(data)*dtypeSizeof; % Navigate to correct dataset fseek(obj.fileID,obj.findSet(istep,iset),'bof'); obj.readHeaderSet(); % Check if datatype/datasize match if dtypeNumeric~=obj.currentSetDatatypeNumeric error('Datatype mismatch: %s,%s',dtype,obj.currentSetDatatype) end if dsize~=obj.currentSetSize error('Datasize mismatch: %d,%d',dsize,obj.currentSetSize) end % Write data fwrite(obj.fileID,data(:),obj.currentSetDatatype,0,obj.Endian); % Verbose output if obj.Verbosity fprintf('Edited dataset %d at timestep #%d\n',obj.currentSet,obj.currentStep); end end % ------------------------------------------------------------------------% % Setter % % ------------------------------------------------------------------------% function setVerbosity(obj,flag) % obj.setVerbosity(flag) % Sets verbosity % Input % flag '1' -> verbose output obj.Verbosity = flag; end function setDebug(obj,flag) % obj.setDebug(flag) % Sets debug flag % Input % flag '1' -> debug output obj.Debug = flag; end % ------------------------------------------------------------------------% % Getter % % ------------------------------------------------------------------------% function [nstep] = getNumTimesteps(obj) % [nstep] = obj.getNumTimesteps() % Gets total number of time steps. nstep = obj.NumTimestep; end function [stime] = getSimulationTime(obj,varargin) % [stime] = obj.getSimulationTime(varargin) % Gets simulation time for one/all time steps % Input % ? istep step index (default: -1, all steps) par = inputParser; addOptional(par,'istep',-1,@isnumeric); parse(par,varargin{:}); if par.Results.istep==-1 stime = obj.timeStep; else stime = obj.timeStep(par.Results.istep); end end function [ndset] = getNumDatasets(obj,istep) % [ndset] = obj.getNumDatasets(istep) % Gets number datasets for a given time step. % Input % istep step index ndset = obj.numSetPerStep(istep); end end %% ------------------------------------------------------------------------%% %% PRIVATE METHODS %% %% ------------------------------------------------------------------------%% methods (Access = private) function readHeaderFile(obj) % Skip to beginning of file fseek(obj.fileID,obj.fileBeg,'bof'); % Determine endianess mfmt = 'aslb'; for fmt=mfmt currentMagic = fread(obj.fileID,1,'int64=>int64',0,fmt); fseek(obj.fileID,obj.fileBeg,'bof'); if currentMagic==obj.magicFile break; end end if currentMagic~=obj.magicFile error('Magic mismatch: invalid file header. %d',currentMagic); end obj.Endian = fmt; % Read header header = fread(obj.fileID,[1,obj.nHeaderFile],'int64=>int64',0,obj.Endian); if obj.Debug fprintf('Read the following file header at %d bytes\n',0); fprintf('%d,%d,%d,%d,%d,%d,%d,%d\n',header); end % Parse version obj.versionMajor = floor(double(header(2))/obj.factorMajor); obj.versionMinor = floor(mod(double(header(2)),obj.factorMajor)/obj.factorMinor); obj.versionPatch = floor(mod(double(header(2)),obj.factorMinor)/obj.factorPatch); obj.CodeVersion = sprintf('%d.%d.%d',obj.versionMajor,obj.versionMinor,obj.versionPatch); obj.UCFVersion = mod(double(header(2)),obj.factorPatch); % Parse time stamp (UTC) obj.creationTimeUnix = double(header(3)); obj.CreationTime = datestr(obj.creationTimeUnix/86400 + datenum(1970,1,1)); % Parse file type obj.typeID = double(header(4)); switch obj.typeID case 0000; obj.Type = 'grid'; case 0010; obj.Type = 'processor grid'; case 1000; obj.Type = 'fluid snapshot'; case 1010; obj.Type = 'scalar snapshot'; case 1999; obj.Type = 'matlab field data'; case 2000; obj.Type = 'particle snapshot'; case 2001; obj.Type = 'particle append'; case 2011; obj.Type = 'particle lagrange'; case 2021; obj.Type = 'particle balancing'; case 2999; obj.Type = 'matlab particle data'; case 3000; obj.Type = 'statistics fluid'; case 3010; obj.Type = 'statistics fluid pure'; case 3020; obj.Type = 'statistics scalar'; otherwise; obj.Type = 'unknown'; end % Parse file class switch floor(obj.typeID/obj.factorTypeIDClass) case 1; obj.Class = 'field'; case 2; obj.Class = 'particle'; case 3; obj.Class = 'statistics'; otherwise; obj.Class = 'unknown'; end % Parse IO rank obj.IORank = double(header(5:8)); end function readHeaderStep(obj) % Read and parse obj.currentStepPosHeader = ftell(obj.fileID); header = fread(obj.fileID,[1,obj.nHeaderStep],'int64=>int64',0,obj.Endian); obj.currentStepPosData = ftell(obj.fileID); currentMagic = header(1); obj.currentStepSize = double(header(2)); obj.currentStepTime = typecast(header(3),'double'); obj.currentStepNumSet = double(header(4)); if obj.Debug fprintf('Read the following step header at %d bytes\n',obj.currentStepPosHeader); fprintf('%d,%d,%f,%d\n',header(1),header(2),typecast(header(3),'double'),header(4)); end % Check if magic is correct if currentMagic~=obj.magicStep error('Magic mismatch: invalid step header. %d',currentMagic); end end function readHeaderSet(obj) % Read and parse obj.currentSetPosHeader = ftell(obj.fileID); header = fread(obj.fileID,[1,obj.nHeaderSet],'int64=>int64',0,obj.Endian); obj.currentSetPosData = ftell(obj.fileID); currentMagic = header(1); obj.currentSetSize = double(header(2)); obj.currentSetDatatypeNumeric = double(header(3)); switch obj.currentSetDatatypeNumeric case 11; obj.currentSetSizeof = 4; obj.currentSetDatatype = 'int32'; case 12; obj.currentSetSizeof = 8; obj.currentSetDatatype = 'int64'; case 21; obj.currentSetSizeof = 4; obj.currentSetDatatype = 'single'; case 22; obj.currentSetSizeof = 8; obj.currentSetDatatype = 'double'; otherwise error('Unknown datatype: %d',obj.currentSetDatatypeNumeric); end obj.currentSetNumParams = double(header(4)); obj.currentSetNumElements = round(obj.currentSetSize/obj.currentSetSizeof); if obj.Debug fprintf('Read the following set header at %d bytes\n',obj.currentSetPosHeader); fprintf('%d,%d,%d,%d\n',header(1),header(2),header(3),header(4)); end % Check if magic is correct if currentMagic~=obj.magicSet error('Magic mismatch: invalid dataset header. %d',currentMagic); end % Read variable number of parameters obj.currentSetParams = fread(obj.fileID,[1,obj.currentSetNumParams],'int64=>int64',0,obj.Endian); if obj.Debug fprintf('with parameters:') for ii=1:obj.currentSetNumParams fprintf(' %d',obj.currentSetParams(ii)); end fprintf('\n'); end end function [flag] = verifyWriteMode(obj) flag = false; switch obj.IOMode case {'edit','create'} flag = true; end end function writeHeaderFile(obj) obj.creationTimeUnix = int64(java.lang.System.currentTimeMillis/1000); % using java for compatability before Matlab2014a header = zeros(1,obj.nHeaderFile,'int64'); header(1) = obj.magicFile; header(2) = obj.versionMajor*obj.factorMajor + ... obj.versionMinor*obj.factorMinor + ... obj.versionPatch*obj.factorPatch + ... obj.versionFile; header(3) = obj.creationTimeUnix; header(4) = int64(obj.typeID); header(5:8) = int64(obj.IORank); fseek(obj.fileID,obj.fileBeg,'bof'); if obj.Debug fprintf('Writing the following file header at %d bytes\n',ftell(obj.fileID)); fprintf('%d,%d,%d,%d,%d,%d,%d,%d\n',header); end fwrite(obj.fileID,header,'int64',0,obj.Endian); obj.isFileHeaderWritten = true; end function writeHeaderStep(obj) if ~obj.isFileHeaderWritten error('No file header has been written yet.'); end fseek(obj.fileID,obj.currentStepPosHeader,'bof'); if obj.Debug fprintf('Writing the following step header at %d bytes\n',ftell(obj.fileID)); fprintf('%d,%d,%f,%d\n',obj.magicStep,obj.currentStepSize,obj.currentStepTime,obj.currentStepNumSet); end fwrite(obj.fileID,obj.magicStep,'int64',0,obj.Endian); fwrite(obj.fileID,obj.currentStepSize,'int64',0,obj.Endian); fwrite(obj.fileID,obj.currentStepTime,'double',0,obj.Endian); fwrite(obj.fileID,obj.currentStepNumSet,'int64',0,obj.Endian); obj.isStepHeaderWritten = true; end function writeHeaderSet(obj) if ~obj.isStepHeaderWritten error('No step header has been written yet.'); end fseek(obj.fileID,obj.currentSetPosHeader,'bof'); header = zeros(1,obj.nHeaderSet,'int64'); header(1) = obj.magicSet; header(2) = obj.currentSetSize; header(3) = obj.currentSetDatatypeNumeric; header(4) = obj.currentSetNumParams; obj.currentSetParams = obj.currentSetParams(1:obj.currentSetNumParams); if obj.Debug fprintf('Writing the following set header at %d bytes\n',ftell(obj.fileID)); fprintf('%d,%d,%d,%d\n',header); fprintf('with parameters:') for ii=1:obj.currentSetNumParams fprintf(' %d',obj.currentSetParams(ii)); end fprintf('\n'); end fwrite(obj.fileID,header,'int64',0,obj.Endian); fwrite(obj.fileID,obj.currentSetParams,'int64',0,obj.Endian); end function [posHeader] = findSet(obj,tstep,dset) % Check input if tstep>obj.NumTimestep error('Out of bounds: timestep. %d, %d',tstep,obj.NumTimestep); end if dset>obj.numSetPerStep(tstep) error('Out of bounds: dataset. %d, %d',dset,obj.NumDataset); end % Navigate to correct set fseek(obj.fileID,obj.posStep(tstep),'bof'); for iset=1:dset-1 obj.readHeaderSet(); fseek(obj.fileID,obj.currentSetSize,'cof'); end posHeader = ftell(obj.fileID); if obj.Debug fprintf('Found step #%d, set #%d at position %d\n',tstep,dset,posHeader) end end function resetPublicProperties(obj) obj.File = []; obj.Type = []; obj.Class = []; obj.Endian = []; obj.CodeVersion = []; obj.UCFVersion = []; obj.NumDataset = []; obj.NumTimestep = []; obj.FileSize = []; obj.CreationTime = []; obj.IOMode = []; obj.IORank = []; obj.Verbosity = []; obj.Debug = []; end function resetPrivateProperties(obj) obj.fileBeg = []; obj.fileEnd = []; obj.typeID = []; obj.ioflag = []; obj.creationTimeUnix = []; obj.versionMajor = []; obj.versionMinor = []; obj.versionPatch = []; obj.versionFile = []; obj.posStep = []; obj.numSetPerStep = []; obj.timeStep = []; obj.isFileHeaderWritten = []; obj.isStepHeaderWritten = []; end function resetCurrentStep(obj) obj.currentStep = []; obj.currentStepPosHeader = []; obj.currentStepPosData = []; obj.currentStepSize = []; obj.currentStepTime = []; obj.currentStepNumSet = []; end function resetCurrentSet(obj) obj.currentSet = []; obj.currentSetPosHeader = []; obj.currentSetPosData = []; obj.currentSetSize = []; obj.currentSetDatatype = []; obj.currentSetDatatypeNumeric = []; obj.currentSetSizeof = []; obj.currentSetNumParams = []; obj.currentSetParams = []; obj.currentSetNumElements = []; end end end