% ReadHMM.m
%
% Routine for reading hidden Markov models in standard HTK format, 
% from a specified file, e.g., 
%
%   fName = '@';
%
% >> clear all; fName='proto'; readhmm; 

%- #define
%-
MAXSTRLEN = 256;
TRUE = 1;
BIGNUM = 1e12;
SMALLNUM = 1e-12;


%-----------------------------------%
%- FUNCTION TO READ A SINGLE MODEL -%
%-----------------------------------%
% void MLReadModel(char *fName, struct modelDef *model)
% {

  %- open model file -%
  ip = fopen(fName, 'r');
  if ip == -1,
    error(['ReadHMM: failed to open model file <' fName '>.']);
  else,
    line = fgets(ip, MAXSTRLEN);
    while (line ~= -1),
      %- parse current line of configuration file -%
      eType = sscanf(line, '%s', 1);


      %- STREAMINFO -%
      if (strncmp(eType, '<STREAMINFO>', 12)),
        [tmp, count] = sscanf(line(length(eType)+1:end), '%d');
        numStream = tmp(1); 
        streamSize = tmp(2);
      end;


      %- VECSIZE -%
      if (strncmp(eType, '<VECSIZE>', 9))
        [tmp, count] = sscanf(line(length(eType)+1:end), '%d', 2);
        vecSize = tmp(1);
        if count < 2,
          vecKind = '<MFCC_D_A_0>';
          durKind = '<NULLD>';
%	  disp(sprintf(' count = %d, setting vector kind to %s', ...
%              count, vecKind));
        else,

          %- This is a temporary bodge (PJBJ 13/05/02)-%
          vecKind = '<MFCC_D_A_0>';
          durKind = '<NULLD>';
	end;
      end;

      %- MODEL LABEL -%
      if (strncmp(eType, '~h', 2)),
        label = sscanf(line(length(eType)+1:end), '%s', 1);
      end;

      %- NUMSTATES -%
      if (strncmp(eType, '<NUMSTATES>', 11)),
        numStates = sscanf(line(length(eType)+1:end), '%d', 1);
        %- allocate memory for state array -%
        stateMean = zeros(numStates, vecSize);
        stateVar = zeros(numStates, vecSize);
        stateTrProb = zeros(numStates, numStates);
      end;


      %- STATE -%
      if (strncmp(eType, '<STATE>', 7)),
        stNum = sscanf(line(length(eType)+1:end), '%d', 1);
        %- read state information from file -%
%        MLgetStateInfo(ip, model, stNum);
% void MLgetStateInfo(FILE *fPtr, struct modelDef *model, int stateNum)
% {
        %- check for mean label -%
        line = fgets(ip, MAXSTRLEN);
        word = sscanf(line, '%s', 1);
        if (strncmp(word, '<MEAN>', 6)),
          %- found <MEAN> -%
          [dim, count] = sscanf(line(length(word)+1:end), '%d', 1);
          if (dim ~= vecSize),
	    error('ERROR reading mean: dim != vecSize');
          else,
            %- allocate space for mean vector -%
            %- For convenience - allocate space for mean reestimation accumulator -%
            %- read in mean vector -%
            for i = 1:vecSize,
              stateMean(stNum, i) = fscanf(ip, '%f', 1);
            end;
            %- read carriage return at end of line -%
            line = fgets(ip, MAXSTRLEN);
          end;
        else,
          error('ERROR reading mean: expecting <MEAN>');
        end;


        %- check for variance label -%
        line = fgets(ip, MAXSTRLEN);
        word = sscanf(line, '%s', 1);
        if (strncmp(word, '<VARIANCE>', 10)),
          %- found <VARIANCE> -%
          [dim, count] = sscanf(line(length(word)+1:end), '%d', 1);
          if (dim ~= vecSize),
            error('ERROR reading variance: dim != vecSize');
          else,
            %- allocate space for variance vector -%
            %- For convenience - allocate space for variance reestimation accumulator -%
            %- Allocate space for log variance vector -%
            %- read in the variance vector -%
            for i = 1:dim,
              stateVar(stNum, i) = fscanf(ip, '%f', 1);
            end;
            %- read carriage return at end of line -%
            line = fgets(ip, MAXSTRLEN);
          end;
        else,
          error('ERROR reading variance: expecting <VARIANCE>');
        end;
      end;
% }


      %- TRANSITION PROBABILITIES -%
      if (strncmp(eType, '<TRANSP>', 8)),
%        getTransProbs(ip, model, numStates);
% void getTransProbs(FILE *fPtr, struct modelDef *model, int numStates)
% {
        %- first create memory for transition probabilities -%
        %- now read transition probabilities -%
        for i = 1:numStates,
          for j = 1:numStates-1,
            stateTrProb(i, j) = fscanf(ip, '%f', 1);
          end;
          %- read final transition prob plus newline -%
          stateTrProb(i, numStates) = fscanf(ip, '%f\n', 1);
        end;
% }
      end;



      %- ENDHMM -%
      line = fgets(ip, MAXSTRLEN);

    end;% while
  end;% if

  %- PJBJ 06/03/02 must close files -%
  tmp = fclose(ip);
  if (tmp == 0),
    disp(['ReadHMM: read and closed model file <' fName '>.']);
  else
    error(['ReadHMM: failed to close model file <' fName '>.']);
  end;

clear MAXSTRLEN dim i j count line word ip tmp eType stNum;
clear domainDim rangeDim;
