3074 lines
		
	
	
		
			77 KiB
		
	
	
	
		
			C#
		
	
	
	
	
	
			
		
		
	
	
			3074 lines
		
	
	
		
			77 KiB
		
	
	
	
		
			C#
		
	
	
	
	
	
/*********************************************************************************************
 | 
						|
 * Copyright 2005 - Volian Enterprises, Inc. All rights reserved.
 | 
						|
 * Volian Enterprises - Proprietary Information - DO NOT COPY OR DISTRIBUTE
 | 
						|
 * ------------------------------------------------------------------------------
 | 
						|
 * $Workfile: ROFST.cs $     $Revision: 13 $
 | 
						|
 * $Author: Kathy $   $Date: 8/31/05 11:32a $
 | 
						|
 *
 | 
						|
 * $History: ROFST.cs $
 | 
						|
 * 
 | 
						|
 * *****************  Version 13  *****************
 | 
						|
 * User: Kathy        Date: 8/31/05    Time: 11:32a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * B2005-032: new groups crashed when writing to ro.fst during approve
 | 
						|
 * sel.
 | 
						|
 * 
 | 
						|
 * *****************  Version 12  *****************
 | 
						|
 * User: Kathy        Date: 8/16/05    Time: 2:52p
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * B2005-030: crash when writing ro.fst for new ro
 | 
						|
 * 
 | 
						|
 * *****************  Version 11  *****************
 | 
						|
 * User: Kathy        Date: 6/21/05    Time: 1:36p
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * FindModROs for approve selected, crash on xyplot with missing end ">"
 | 
						|
 * 
 | 
						|
 * *****************  Version 10  *****************
 | 
						|
 * User: Jsj          Date: 6/02/05    Time: 11:31a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * fix for approving with conditional ROs
 | 
						|
 * 
 | 
						|
 * *****************  Version 9  *****************
 | 
						|
 * User: Jsj          Date: 5/20/05    Time: 9:21a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * fixed getro for cases when using unit specific info to process the RO
 | 
						|
 * return value.
 | 
						|
 * 
 | 
						|
 * *****************  Version 8  *****************
 | 
						|
 * User: Jsj          Date: 5/17/05    Time: 11:48a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * fixed approve graphic bug, added default graphic extension as part of
 | 
						|
 * ROFST class initialization, code cleanup
 | 
						|
 * 
 | 
						|
 * *****************  Version 7  *****************
 | 
						|
 * User: Kathy        Date: 5/11/05    Time: 9:26a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * add close method
 | 
						|
 * 
 | 
						|
 * *****************  Version 6  *****************
 | 
						|
 * User: Jsj          Date: 4/07/05    Time: 11:15a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * fixes
 | 
						|
 * 
 | 
						|
 * *****************  Version 5  *****************
 | 
						|
 * User: Jsj          Date: 3/31/05    Time: 9:16a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * 
 | 
						|
 * *****************  Version 4  *****************
 | 
						|
 * User: Jsj          Date: 3/28/05    Time: 12:18p
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * 
 | 
						|
 * *****************  Version 3  *****************
 | 
						|
 * User: Jsj          Date: 3/22/05    Time: 9:52a
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * March 22 2005 update for merge
 | 
						|
 * 
 | 
						|
 * *****************  Version 2  *****************
 | 
						|
 * User: Jsj          Date: 3/14/05    Time: 1:36p
 | 
						|
 * Updated in $/LibSource/ROFST
 | 
						|
 * update
 | 
						|
 * 
 | 
						|
 * *****************  Version 1  *****************
 | 
						|
 * User: Jsj          Date: 3/10/05    Time: 3:53p
 | 
						|
 * Created in $/LibSource/ROFST
 | 
						|
 * 
 | 
						|
 * *****************  Version 1  *****************
 | 
						|
 * User: Jsj          Date: 3/10/05    Time: 3:49p
 | 
						|
 * Created in $/LibSource/ROFST/ROFST
 | 
						|
 * 
 | 
						|
  *********************************************************************************************/
 | 
						|
using System;
 | 
						|
using System.IO;
 | 
						|
using System.Windows.Forms;
 | 
						|
using System.Text;
 | 
						|
using System.Collections;
 | 
						|
using VlnStatus;
 | 
						|
using Utils;
 | 
						|
 | 
						|
/*
 | 
						|
 * This namespace is used in both VE-PROMS and the RO Editor programs.
 | 
						|
 */
 | 
						|
namespace ROFST_FILE
 | 
						|
{
 | 
						|
	/*
 | 
						|
	 * Globally used functions amoung a few of the classes in this namespace
 | 
						|
	 */
 | 
						|
	public class ROProcessTools
 | 
						|
	{
 | 
						|
		// For now, have hooks to set and get the current
 | 
						|
		// procedure number along with the Maxium Procedure
 | 
						|
		// Number length.  The 16-bit code used globals
 | 
						|
		// jsj - 6/2/2005
 | 
						|
 | 
						|
		private static string PNumber = " "; // default to blank
 | 
						|
		private static int mxPrcLen = 30; // default to 30 chars
 | 
						|
 | 
						|
		static ROProcessTools()
 | 
						|
		{
 | 
						|
		}
 | 
						|
		
 | 
						|
		public static string ProcedureNumber
 | 
						|
		{
 | 
						|
			set { PNumber = value.ToString();}
 | 
						|
			get { return PNumber; }
 | 
						|
		}
 | 
						|
 | 
						|
		public static int MaxProcNumLen
 | 
						|
		{
 | 
						|
			set { mxPrcLen = (int)value;}
 | 
						|
			get { return mxPrcLen;}
 | 
						|
		}
 | 
						|
	
 | 
						|
		public static string UnitSpecific(string str, int len, int trm, int maxPrcNumLen)
 | 
						|
		{
 | 
						|
			// This routine retrieves the procedure number format from the
 | 
						|
			// current directory and uses it to adjust the procedure number
 | 
						|
			// in the specified string
 | 
						|
			string retvalu="";
 | 
						|
			string asis="#";
 | 
						|
			string pnum;
 | 
						|
			if( str == null || str.Length == 0 ) return null;
 | 
						|
			/*
 | 
						|
			 * Bug fix: B2005-017 3/2/2005
 | 
						|
			 * Need to use the largest procedure number length that's in the
 | 
						|
			 * SET.DFF file.  "LargestNumber" is the largest length after the
 | 
						|
			 * procedure number is replaced via the SET.INI file "replace" list.
 | 
						|
			 *
 | 
						|
				if(len==0)len=LargestNumber;
 | 
						|
			 */
 | 
						|
			if(len==0)len=maxPrcNumLen; //LargestRawSetNumber
 | 
						|
			string mstr;
 | 
						|
			PrivateProfile proc_ini = new PrivateProfile("proc.ini");
 | 
						|
			mstr = proc_ini.Attr("unit", "procedure number");
 | 
						|
			if (mstr == null) mstr = asis;
 | 
						|
			pnum=mstr;
 | 
						|
			if(pnum.Equals(asis))
 | 
						|
			{
 | 
						|
				retvalu=str;
 | 
						|
			} 
 | 
						|
			else if (!pnum.Equals("") && pnum[0] == '!') 
 | 
						|
			{
 | 
						|
				if (File.Exists("set.ini"))
 | 
						|
				{
 | 
						|
					string p = str;
 | 
						|
					string q, tonum;
 | 
						|
					StringBuilder rbldr = new StringBuilder();
 | 
						|
					int newl, dw, cnt=0, lstr;
 | 
						|
 | 
						|
					p = p.TrimStart(" ".ToCharArray());
 | 
						|
					lstr = p.Length;
 | 
						|
					if (len > lstr) len = lstr;
 | 
						|
					mstr = p.Substring(0,len);
 | 
						|
					mstr = mstr.TrimEnd(" \t\r\n".ToCharArray());
 | 
						|
					/* debug
 | 
						|
					string debugstr = "|" + mstr + "|";
 | 
						|
					*/
 | 
						|
		
 | 
						|
					PrivateProfile set_ini = new PrivateProfile("set.ini");
 | 
						|
 | 
						|
					tonum = set_ini.Attr("replace", mstr);
 | 
						|
					if (tonum == null || tonum.Equals("")) tonum = mstr;
 | 
						|
					newl = tonum.Length;
 | 
						|
					dw = newl - (lstr);
 | 
						|
 | 
						|
					q = str; p = tonum;
 | 
						|
					int strptr=0;
 | 
						|
					for (strptr=0; str[strptr] == ' '; strptr++)
 | 
						|
						rbldr.Append(" ");//initial spaces
 | 
						|
					int pptr=0;
 | 
						|
					while (cnt < len) 
 | 
						|
					{
 | 
						|
						if (tonum!=null && pptr < tonum.Length) 
 | 
						|
							rbldr.Append(tonum[pptr++]);
 | 
						|
						else if (trm == 1) break;
 | 
						|
						else if (cnt < lstr) rbldr.Append(" ");
 | 
						|
						else break;
 | 
						|
						cnt++;
 | 
						|
					}
 | 
						|
					if (trm==0) 
 | 
						|
					{
 | 
						|
						strptr+=len;
 | 
						|
						while (str!=null && strptr < str.Length) 
 | 
						|
							rbldr.Append(str[strptr++]);
 | 
						|
					}
 | 
						|
					retvalu = rbldr.ToString();
 | 
						|
				}
 | 
						|
				else
 | 
						|
				{
 | 
						|
					retvalu=str;
 | 
						|
				}
 | 
						|
			} 
 | 
						|
			else 
 | 
						|
			{
 | 
						|
				StringBuilder rbldr = new StringBuilder();
 | 
						|
				// create pointers to use to transfer info
 | 
						|
				int pnumPtr = 0, strPtr=0, endStrPtr = str.Length-1;
 | 
						|
				string pad = "";
 | 
						|
				// determine if the procedure number should be padded instead
 | 
						|
				if(str[0]==' ')pad=" ";
 | 
						|
				// copy from the procedure number definition to the pound symbol
 | 
						|
				if (!pnum.Equals(""))
 | 
						|
				{
 | 
						|
					while(pnumPtr < pnum.Length && pnum[pnumPtr] != '#')
 | 
						|
					{
 | 
						|
						rbldr.Append(((!pad.Equals(""))? pad : pnum[pnumPtr].ToString()));
 | 
						|
						pnumPtr++;
 | 
						|
					}
 | 
						|
					// skip the pound sign
 | 
						|
					if(pnumPtr < pnum.Length && pnum[pnumPtr]!=0)pnumPtr++;
 | 
						|
				}
 | 
						|
				// assuming that the procedure number occurs at the beginning of
 | 
						|
				// str, check to see where it ends
 | 
						|
				if(str.Length > len)endStrPtr=len-1;
 | 
						|
				// find the end of the procedure number
 | 
						|
				while(endStrPtr > strPtr && str[endStrPtr]==' ')endStrPtr--;
 | 
						|
				// copy the procedure number
 | 
						|
				while(strPtr <= endStrPtr)rbldr.Append(str[strPtr++]);
 | 
						|
				// copy the rest of the format
 | 
						|
				while(pnumPtr < pnum.Length)
 | 
						|
				{
 | 
						|
					rbldr.Append(((!pad.Equals(""))? pad : pnum[pnumPtr].ToString()));
 | 
						|
					pnumPtr++;
 | 
						|
				}
 | 
						|
				// copy the rest of the given string
 | 
						|
				while(strPtr < str.Length)rbldr.Append(str[strPtr++]);
 | 
						|
				retvalu = rbldr.ToString();
 | 
						|
			}
 | 
						|
			return retvalu;
 | 
						|
		}
 | 
						|
 | 
						|
		public static int matchingBrace(string str)
 | 
						|
		{
 | 
						|
			int strptr = 0;
 | 
						|
			int  level=1;
 | 
						|
			while(level > 0)
 | 
						|
			{
 | 
						|
				strptr++;
 | 
						|
				switch(str[strptr])
 | 
						|
				{
 | 
						|
					case '{':
 | 
						|
						level++;
 | 
						|
						break;
 | 
						|
					case '}':
 | 
						|
						level--;
 | 
						|
						break;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return strptr;
 | 
						|
		}
 | 
						|
 | 
						|
		public static int nextDelimiter(string delim,string str,int l)
 | 
						|
		{
 | 
						|
			int nxtdelim = -1;
 | 
						|
			int strptr = 0;
 | 
						|
			while(l-- > 0 && (nxtdelim == -1))
 | 
						|
			{
 | 
						|
				if (delim.IndexOf(str[strptr])>-1)
 | 
						|
					nxtdelim = strptr;
 | 
						|
				strptr++;
 | 
						|
			}
 | 
						|
			return nxtdelim;
 | 
						|
		}
 | 
						|
 | 
						|
		public static string getProfile(string grp, string nam)
 | 
						|
		{
 | 
						|
			return getProfile(grp,nam,0);
 | 
						|
		}
 | 
						|
 | 
						|
		public static string getProfile(string grp, string nam, int flag)
 | 
						|
		{
 | 
						|
			string buff=null;
 | 
						|
			if( grp==null ) return null;
 | 
						|
			PrivateProfile proc_ini = new PrivateProfile("proc.ini");
 | 
						|
			buff = proc_ini.Attr(grp,nam);
 | 
						|
			if (buff == null)
 | 
						|
				buff = "";
 | 
						|
			if(buff.Equals(""))
 | 
						|
			{
 | 
						|
				if (flag == 0)
 | 
						|
					buff = "<" + grp + "-" + nam + ">";
 | 
						|
				else
 | 
						|
					return null;
 | 
						|
			}
 | 
						|
			return buff;
 | 
						|
		}
 | 
						|
 | 
						|
		public static string evaluate(string str,int len)
 | 
						|
		{
 | 
						|
			string retval=null;
 | 
						|
			string swhir = "PSU"; /* order inwhich to check */
 | 
						|
			string pn;
 | 
						|
			if(str[1]=='-')
 | 
						|
			{
 | 
						|
				int swptr = swhir.IndexOf((str.ToUpper())[0]);
 | 
						|
				byte swchar = 0;
 | 
						|
				if( swptr > -1 ) swchar = (byte)swhir[swptr];
 | 
						|
 | 
						|
				byte sav=(byte)str[len];
 | 
						|
				str = str.Substring(0,len);
 | 
						|
				while ((swptr > -1) && (swhir[swptr] != 0) && retval == null)
 | 
						|
				{
 | 
						|
					if (swchar == 0) swchar = (byte)str[0];
 | 
						|
					switch((char)swchar)
 | 
						|
					{
 | 
						|
						case 'U':
 | 
						|
							retval=getProfile("Unit",str.Substring(2),swhir[swptr]);
 | 
						|
							break;
 | 
						|
						case 'S':
 | 
						|
							retval=getProfile("Procedure Set",str.Substring(2),swhir[swptr]);
 | 
						|
							break;
 | 
						|
						case 'P':
 | 
						|
							pn = UnitSpecific(PNumber, 0, 1, mxPrcLen);
 | 
						|
							retval=getProfile(pn,str.Substring(2),swhir[swptr]);
 | 
						|
							break;
 | 
						|
					}
 | 
						|
					if (retval == null)
 | 
						|
						swchar= (byte)swhir[++swptr];
 | 
						|
				}
 | 
						|
				StringBuilder sb1 = new StringBuilder(str);
 | 
						|
				sb1.Insert(len,sav);
 | 
						|
				str = sb1.ToString();
 | 
						|
			} 
 | 
						|
			else if(len==1 && (str.ToUpper())[0]=='U') 
 | 
						|
			{
 | 
						|
				retval=getProfile("Unit","Number");
 | 
						|
			} 
 | 
						|
			else if(len==2 && str.ToUpper().StartsWith("ID")) 
 | 
						|
			{
 | 
						|
				retval=getProfile("Unit","ID");
 | 
						|
			}
 | 
						|
			if(retval == null)
 | 
						|
			{
 | 
						|
				retval=str.Substring(0,len+2>str.Length?str.Length:len+2);
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	/// <summary>
 | 
						|
	/// Summary description for ROFSTHeader.
 | 
						|
	/// </summary>
 | 
						|
 | 
						|
	public class FST_FileHeader
 | 
						|
	{
 | 
						|
		public int hSize; // size of header structure (record)
 | 
						|
		public short hYear;// year this header was designed (1993)
 | 
						|
		public byte hMonth;// month this header was designed (10)
 | 
						|
		public byte hDay;// day this header was designed (25)
 | 
						|
		public short hcYear;// FST file creation year
 | 
						|
		public byte hcMonth;// FST file creation month
 | 
						|
		public byte hcDay;// FST file creation day
 | 
						|
		public byte hcHour;// FST file creation hour
 | 
						|
		public byte hcMin;// FST file creation minute
 | 
						|
		public byte hcSec;// FST file creation seconds
 | 
						|
		public byte hcHund;// FST file creation hundredth seconds
 | 
						|
		public uint dboffset;// end of RO data, start of database list
 | 
						|
 | 
						|
 | 
						|
		// Constructors
 | 
						|
		// default constructor creates with zero'd out values
 | 
						|
		public FST_FileHeader()
 | 
						|
		{
 | 
						|
			hSize = 0;
 | 
						|
			hYear = 0;
 | 
						|
			hMonth =  0;
 | 
						|
			hDay = 0;
 | 
						|
			hcYear = 0;
 | 
						|
			hcMonth = 0;
 | 
						|
			hcDay = 0;
 | 
						|
			hcHour = 0;
 | 
						|
			hcMin = 0;
 | 
						|
			hcSec = 0;
 | 
						|
			hcHund = 0;
 | 
						|
			dboffset = 0;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Constructor that initializes with pass in values
 | 
						|
		FST_FileHeader(int Size, short Year, byte Month, byte Day, short cYear, byte cMonth,
 | 
						|
			byte cDay, byte cHour, byte cMin, byte cSec, byte cHund, uint offset)
 | 
						|
		{
 | 
						|
			hSize = Size;
 | 
						|
			hYear = Year;
 | 
						|
			hMonth =  Month;
 | 
						|
			hDay = Day;
 | 
						|
			hcYear = cYear;
 | 
						|
			hcMonth = cMonth;
 | 
						|
			hcDay = cDay;
 | 
						|
			hcHour = cHour;
 | 
						|
			hcMin = cMin;
 | 
						|
			hcSec = cSec;
 | 
						|
			hcHund = cHund;
 | 
						|
			dboffset = offset;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void Read (BinaryReader br)
 | 
						|
		{
 | 
						|
			hSize = br.ReadInt32();
 | 
						|
			hYear = br.ReadInt16();
 | 
						|
			hMonth = br.ReadByte();
 | 
						|
			hDay = br.ReadByte();
 | 
						|
			hcYear = br.ReadInt16();
 | 
						|
			hcMonth = br.ReadByte();
 | 
						|
			hcDay = br.ReadByte();
 | 
						|
			hcHour = br.ReadByte();
 | 
						|
			hcMin = br.ReadByte();
 | 
						|
			hcSec = br.ReadByte();
 | 
						|
//			byte tbyte = br.ReadByte();
 | 
						|
//			hcHund = (sbyte)tbyte;
 | 
						|
			hcHund = br.ReadByte();
 | 
						|
			dboffset = br.ReadUInt32();
 | 
						|
 | 
						|
			//			return new FST_FileHeader(fSize,fYear,fMonth,fDay,
 | 
						|
			//				fcYear,fcMonth,fcDay,fcHour,fcMin,fcSec,fcHund,fdboffset);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void Write (BinaryWriter bw)
 | 
						|
		{
 | 
						|
			bw.Write(hSize);
 | 
						|
			bw.Write(hYear);
 | 
						|
			bw.Write(hMonth);
 | 
						|
			bw.Write(hDay);
 | 
						|
			bw.Write(hcYear);
 | 
						|
			bw.Write(hcMonth);
 | 
						|
			bw.Write(hcDay);
 | 
						|
			bw.Write(hcHour);
 | 
						|
			bw.Write(hcMin);
 | 
						|
			bw.Write(hcSec);
 | 
						|
			bw.Write(hcHund);
 | 
						|
			bw.Write(dboffset);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public int GetStructSize()
 | 
						|
		{
 | 
						|
			int rtval = 0;
 | 
						|
 | 
						|
			// You can only use sizeof() in unsafe compiles
 | 
						|
			// so we'll do it by hand...
 | 
						|
			// each number is the number of bytes
 | 
						|
 | 
						|
			rtval += 4; //sizeof(hSize);
 | 
						|
			rtval += 2; //sizeof(hYear);
 | 
						|
			rtval += 1; //sizeof(hMonth);
 | 
						|
			rtval += 1; //sizeof(hDay);
 | 
						|
			rtval += 2; //sizeof(hcYear);
 | 
						|
			rtval += 1; //sizeof(hcMonth);
 | 
						|
			rtval += 1; //sizeof(hcDay);
 | 
						|
			rtval += 1; //sizeof(hcHour);
 | 
						|
			rtval += 1; //sizeof(hcMin);
 | 
						|
			rtval += 1; //sizeof(hcSec);
 | 
						|
			rtval += 1; //sizeof(hcHund);
 | 
						|
			rtval += 4; //sizeof(dboffset);
 | 
						|
 | 
						|
			return rtval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void SetHeader(uint offset)
 | 
						|
		{
 | 
						|
			hSize = GetStructSize();
 | 
						|
			hYear = 1993;
 | 
						|
			hMonth = 10;
 | 
						|
			hDay = 25;
 | 
						|
			DateTime dt = DateTime.Now;
 | 
						|
			hcYear = (short)dt.Year;
 | 
						|
			hcMonth = (byte)dt.Month;
 | 
						|
			hcDay = (byte)dt.Day;
 | 
						|
			hcHour = (byte)dt.Hour;
 | 
						|
			hcMin = (byte)dt.Minute;
 | 
						|
			hcSec = (byte)dt.Second;
 | 
						|
			hcHund = (byte)dt.Millisecond;
 | 
						|
			dboffset = offset;
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	public class ROFST_DbInfo
 | 
						|
	{
 | 
						|
		public ushort dbiID; // Number part of table name (RO000002 => 02)
 | 
						|
		public ushort dbiType; // database type (Setpoint,Graphics,User defined)
 | 
						|
		public ushort dbiAW; // length of widest AccPageID
 | 
						|
		public uint dbiGL; // FST file position of this group
 | 
						|
		public uint dbiIL; // FST file position of list of ROIDs
 | 
						|
		public uint dbiAL; // FST file position of list of AccPageIDs
 | 
						|
		public uint dbiEND; // FST file position of the end of this group
 | 
						|
		// !!! make sure to convert strings to char arrays when writing
 | 
						|
		public string dbiTitle; // database title
 | 
						|
		public string dbiAP;  // AccPageID Prefix (ex. SP- )
 | 
						|
 | 
						|
 | 
						|
		// Constructors
 | 
						|
		// default constructor creates with zero'd out values
 | 
						|
		public ROFST_DbInfo()
 | 
						|
		{
 | 
						|
			dbiID = 0;
 | 
						|
			dbiType = 0;
 | 
						|
			dbiAW = 0;
 | 
						|
			dbiGL = 0;
 | 
						|
			dbiIL = 0;
 | 
						|
			dbiAL = 0;
 | 
						|
			dbiEND = 0;
 | 
						|
			dbiTitle = ""; 
 | 
						|
			dbiAP = "";
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Constructor that initializes with pass in values
 | 
						|
		ROFST_DbInfo(ushort ID, ushort Type, ushort AW, uint GL, uint IL, uint AL,	uint END, 
 | 
						|
			string Title, string dbiAP)
 | 
						|
		{
 | 
						|
			dbiID = ID;
 | 
						|
			dbiType = Type;
 | 
						|
			dbiAW = AW;
 | 
						|
			dbiGL = GL;
 | 
						|
			dbiIL = IL;
 | 
						|
			dbiAL = AL;
 | 
						|
			dbiEND = END;
 | 
						|
			dbiTitle = Title; 
 | 
						|
			dbiAP = dbiAP;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void WriteUntAndShort(BinaryWriter bw)
 | 
						|
		{
 | 
						|
			bw.Write(dbiID);
 | 
						|
			bw.Write(dbiType);
 | 
						|
			bw.Write(dbiAW);
 | 
						|
			bw.Write(dbiGL);
 | 
						|
			bw.Write(dbiIL);
 | 
						|
			bw.Write(dbiAL);
 | 
						|
			bw.Write(dbiEND);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		void WriteString(BinaryWriter bw, string str)
 | 
						|
		{
 | 
						|
			byte nullbyte = 0;
 | 
						|
			byte []wrBytes = new byte[str.Length + 1];
 | 
						|
			int i;
 | 
						|
			for(i =0; i < str.Length; i++)
 | 
						|
			{
 | 
						|
//				byte WrByte;
 | 
						|
//				WrByte = (byte)str[i];
 | 
						|
//				bw.Write(WrByte);
 | 
						|
				wrBytes[i] = (byte)str[i];
 | 
						|
			}
 | 
						|
			wrBytes[i] = nullbyte;
 | 
						|
			bw.Write(wrBytes);
 | 
						|
//			bw.Write(nullbyte);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void WriteStrings(BinaryWriter bw)
 | 
						|
		{
 | 
						|
			WriteString(bw,dbiTitle);
 | 
						|
			WriteString(bw,dbiAP);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public uint GetStructSize()
 | 
						|
		{
 | 
						|
			uint rtval = 0;
 | 
						|
 | 
						|
			// You can only use sizeof() in unsafe compiles
 | 
						|
			// so we'll do it by hand...
 | 
						|
			// each number is the number of bytes
 | 
						|
 | 
						|
			rtval += 2; //sizeof(dbiID);
 | 
						|
			rtval += 2; //sizeof(dbiType);
 | 
						|
			rtval += 2; //sizeof(dbiAW);
 | 
						|
			rtval += 4; //sizeof(dbiGL);
 | 
						|
			rtval += 4; //sizeof(dbiIL);
 | 
						|
			rtval += 4; //sizeof(dbiAL);
 | 
						|
			rtval += 4; //sizeof(dbiEND);
 | 
						|
			rtval += 4; //sizeof(uint); // to simulate the (char *) in the old code (16 datatypes)
 | 
						|
			rtval += 4; //sizeof(uint); // to simulate the (char *) in the old code (16 datatypes)
 | 
						|
 | 
						|
			return rtval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void Load(BinaryReader br)
 | 
						|
		{
 | 
						|
			ReadValues(br);
 | 
						|
		}
 | 
						|
 | 
						|
		//		public void ReadStrings(BinaryReader br)
 | 
						|
		//		{
 | 
						|
		//			dbiTitle = ROFST_File.LoadString(br);
 | 
						|
		//			dbiAP = ROFST_File.LoadString(br);
 | 
						|
		//		}
 | 
						|
 | 
						|
 | 
						|
		public void ReadValues(BinaryReader br)
 | 
						|
		{
 | 
						|
			dbiID = br.ReadUInt16();
 | 
						|
			dbiType = br.ReadUInt16();
 | 
						|
			dbiAW = br.ReadUInt16();
 | 
						|
			dbiGL = br.ReadUInt32();
 | 
						|
			dbiIL = br.ReadUInt32();
 | 
						|
			dbiAL = br.ReadUInt32();
 | 
						|
			dbiEND = br.ReadUInt32();
 | 
						|
			uint tmp = br.ReadUInt32();
 | 
						|
			uint tmp1 = br.ReadUInt32();
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
 | 
						|
	// structure to hold information to add a new group
 | 
						|
	public struct AddGroup
 | 
						|
	{
 | 
						|
		public uint grp_id;
 | 
						|
		public uint grp_parid;
 | 
						|
		public string grp_name;
 | 
						|
		public short grp_type;
 | 
						|
		public short grp_stat;
 | 
						|
		public uint grp_offset;
 | 
						|
		public int grp_pargrpidx;
 | 
						|
 | 
						|
 | 
						|
		// These functions are needed to update values when
 | 
						|
		// referenced from the ArrayLists (allNewGrps)
 | 
						|
//		public void OR_grp_type(short val)
 | 
						|
//		{
 | 
						|
//			ushort gtype = (ushort)grp_type;
 | 
						|
//			gtype |= (ushort)val;
 | 
						|
//			grp_type = (short)gtype;
 | 
						|
//		}
 | 
						|
//
 | 
						|
//
 | 
						|
//		public void SET_grp_parid(uint val)
 | 
						|
//		{
 | 
						|
//			grp_parid = val;
 | 
						|
//		}
 | 
						|
//	
 | 
						|
//	
 | 
						|
//		public void SET_grp_pargrpidx(int val)
 | 
						|
//		{
 | 
						|
//			grp_pargrpidx = val;
 | 
						|
//		}
 | 
						|
//
 | 
						|
//
 | 
						|
//		public void SET_grp_stat(short val)
 | 
						|
//		{
 | 
						|
//			grp_stat = val;
 | 
						|
//		}
 | 
						|
//
 | 
						|
//
 | 
						|
//		public void SET_grp_offset(uint val)
 | 
						|
//		{
 | 
						|
//			grp_offset = val;
 | 
						|
//		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	// structure to hold information to add a new RO
 | 
						|
	public struct AddRO
 | 
						|
	{
 | 
						|
		public uint ro_id;
 | 
						|
		public uint ro_parid;
 | 
						|
		public string ro_num;
 | 
						|
		public string ro_desc;
 | 
						|
		public string ro_val;
 | 
						|
		public short ro_type;
 | 
						|
		public short ro_stat;
 | 
						|
		public int ro_offset;
 | 
						|
		public int ro_pargrpidx; // index into allNewGrps
 | 
						|
 | 
						|
 | 
						|
		// These functions are needed to update values when
 | 
						|
		// referenced from the ArrayLists (allNewRos)
 | 
						|
//		public void SET_ro_pargrpidx(int val)
 | 
						|
//		{
 | 
						|
//			ro_pargrpidx = val;
 | 
						|
//		}
 | 
						|
//	
 | 
						|
//	
 | 
						|
//		public void SET_ro_parid(uint val)
 | 
						|
//		{
 | 
						|
//			ro_parid = val;
 | 
						|
//		}
 | 
						|
//
 | 
						|
//
 | 
						|
//		public void SET_ro_stat(short val)
 | 
						|
//		{
 | 
						|
//			ro_stat = val;
 | 
						|
//		}
 | 
						|
//
 | 
						|
//
 | 
						|
//		public void SET_ro_offset(int val)
 | 
						|
//		{
 | 
						|
//			ro_offset = val;
 | 
						|
//		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	// structure to hold RO difference information
 | 
						|
	public struct DiffRO
 | 
						|
	{
 | 
						|
		public uint id;
 | 
						|
		public short type;
 | 
						|
		public string desc;
 | 
						|
		public string val;
 | 
						|
		public uint oldoff; // index into old RO.FST file (approved)
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	// RO update info arrays.
 | 
						|
	// one of these structures is created from each RO database
 | 
						|
	// (Setpoints, Graphics, User Defined, etc.)
 | 
						|
	public struct dbinew
 | 
						|
	{
 | 
						|
		public ArrayList aryAddedRO;
 | 
						|
		public ArrayList aryAddedGroup;
 | 
						|
		public ArrayList aryAddedDiff;
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	// structure to store file positions in the RO.FST file
 | 
						|
	public struct locinc
 | 
						|
	{
 | 
						|
		public uint maxloc;
 | 
						|
		public int inc;
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	/*
 | 
						|
	** Structure of the graphics' values.
 | 
						|
	** LocalGrfStats ( in ROFST_File class) is used to hold the current 
 | 
						|
	** values "locally" in memory 
 | 
						|
	*/
 | 
						|
	public struct GrfStats 
 | 
						|
	{
 | 
						|
		public string PixFileName;
 | 
						|
		public int PixFileTime;
 | 
						|
		public short PixFileHeight;
 | 
						|
		public short PixFileWidth;
 | 
						|
 | 
						|
		public void Clear()
 | 
						|
		{
 | 
						|
			PixFileName="";
 | 
						|
			PixFileTime = 0;
 | 
						|
			PixFileHeight = 0;
 | 
						|
			PixFileWidth = 0;
 | 
						|
		}
 | 
						|
 | 
						|
		public void Load(string instr)
 | 
						|
		{
 | 
						|
			short DeciPerRow = 120;
 | 
						|
			short DeciPerCol = 60;
 | 
						|
			StringBuilder sb = new StringBuilder();
 | 
						|
			int i=0;
 | 
						|
			bool nl = false;
 | 
						|
			/*
 | 
						|
			sscanf(retval,"%s\n%08lx\n%04x\n%04x",LocalGrfStats.PixFileName,
 | 
						|
				&LocalGrfStats.PixFileTime,&LocalGrfStats.PixFileHeight,
 | 
						|
				&LocalGrfStats.PixFileWidth);
 | 
						|
			LocalGrfStats.PixFileHeight *= DeciPerRow;
 | 
						|
			LocalGrfStats.PixFileWidth *= DeciPerCol;
 | 
						|
			*/
 | 
						|
			while (!nl && (instr[i]!= 0))
 | 
						|
			{
 | 
						|
				if (instr[i]=='\n')
 | 
						|
					nl=true;
 | 
						|
				else
 | 
						|
					sb.Append(instr[i]);
 | 
						|
				i++;
 | 
						|
			}
 | 
						|
			if (nl)
 | 
						|
			{
 | 
						|
				PixFileName = sb.ToString();
 | 
						|
			}
 | 
						|
 | 
						|
			nl = false;
 | 
						|
			sb.Remove(0,sb.Length);
 | 
						|
			while (!nl && (instr[i]!=0))
 | 
						|
			{
 | 
						|
				if (instr[i]=='\n')
 | 
						|
					nl=true;
 | 
						|
				else
 | 
						|
					sb.Append(instr[i]);
 | 
						|
				i++;
 | 
						|
			}
 | 
						|
			PixFileTime = Convert.ToInt32(sb.ToString(),16);
 | 
						|
 | 
						|
			nl = false;
 | 
						|
			sb.Remove(0,sb.Length);
 | 
						|
			while (!nl && (instr[i]!=0))
 | 
						|
			{
 | 
						|
				if (instr[i]=='\n')
 | 
						|
					nl=true;
 | 
						|
				else
 | 
						|
					sb.Append(instr[i]);
 | 
						|
				i++;
 | 
						|
			}
 | 
						|
			PixFileHeight = Convert.ToInt16(sb.ToString(),16);
 | 
						|
			PixFileHeight *= DeciPerRow;
 | 
						|
 | 
						|
			sb.Remove(0,sb.Length);
 | 
						|
			while ((i < instr.Length) && (instr[i]!=0))
 | 
						|
			{
 | 
						|
				sb.Append(instr[i]);
 | 
						|
				i++;
 | 
						|
			}
 | 
						|
			PixFileWidth = Convert.ToInt16(sb.ToString(),16);
 | 
						|
			PixFileWidth *= DeciPerCol;
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	public class ROFST_File
 | 
						|
	{
 | 
						|
		public enum ROTypes
 | 
						|
		{
 | 
						|
			None=0, Text=1, Table=2, Plot=4, Figure=8
 | 
						|
		};
 | 
						|
 | 
						|
		private string [] UnitVariables =
 | 
						|
			{
 | 
						|
				"All of the following",//
 | 
						|
				"Number",		// 1L; - 1, 2 etc.
 | 
						|
				"Other Number",	// 2L; - 2, 1 etc.
 | 
						|
				"Text",			// 3L; - One, Two etc. or Unit One, Unit Two
 | 
						|
				"Other Text",	// 4L; - Two, One etc. or Unit Two, Unit One
 | 
						|
				"ID",			// 5L; - 1Bw, 2Bw etc.
 | 
						|
				"Other ID",		// 6L; - 2Bw, 1Bw etc.
 | 
						|
				"Name",			// 7L; - Braidwood Unit 1
 | 
						|
				"Other Name"	// 8L; - Braidwood Unit 2
 | 
						|
			};
 | 
						|
		private uint NumUnitVariables =9;
 | 
						|
 | 
						|
 | 
						|
		private ArrayList [] allNewRos; // new ROs
 | 
						|
		private ArrayList [] allDifferences; // changed ROs
 | 
						|
		private ArrayList [] allNewGrps; // new Groups
 | 
						|
		private ArrayList allLocations; // positions in RO.FST
 | 
						|
 | 
						|
 | 
						|
		private int curTblIdx=0; // index into allxxxxx arraylists
 | 
						|
		private uint NewID = 0xFFFF0000;
 | 
						|
		private uint whereisgl = 0;
 | 
						|
		private ushort maxaw=0;
 | 
						|
		private ushort maxtype=0;
 | 
						|
		private int lastLocationIdx = 0;
 | 
						|
 | 
						|
		public BinaryReader brROFst; // file handle into RO.FST
 | 
						|
		public ArrayList DatabasesInfo; // Holds the current RO.FST data
 | 
						|
		public ArrayList dbiNewInfo; // will hold new RO.FST data
 | 
						|
 | 
						|
		public short numDatabases; // number of databases in RO.FST
 | 
						|
		public FST_FileHeader Header;
 | 
						|
		//		public UserRunTime usrRunTime;
 | 
						|
		public string DirPath;
 | 
						|
 | 
						|
		public string DefaultGraphicFileExt = "";
 | 
						|
 | 
						|
		// RO Graphics information
 | 
						|
		GrfStats LocalGrfStats;
 | 
						|
 | 
						|
		// constructor loads ro.fst databases
 | 
						|
		//		public ROFST(string path, UserRunTime urt)
 | 
						|
		public ROFST_File(string path)
 | 
						|
		{
 | 
						|
			try
 | 
						|
			{
 | 
						|
				brROFst = new BinaryReader(File.Open(path,System.IO.FileMode.Open,System.IO.FileAccess.ReadWrite,FileShare.ReadWrite));
 | 
						|
			}
 | 
						|
			catch (Exception e)
 | 
						|
			{
 | 
						|
				MessageBox.Show("Open "+path+"\n\n" + e.Message,"RO.FST Error");
 | 
						|
				return;
 | 
						|
			}
 | 
						|
			DirPath = path; // path of RO.FST file
 | 
						|
 | 
						|
			//			usrRunTime = urt;
 | 
						|
 | 
						|
			// Read the RO.FST header information
 | 
						|
			Header = new FST_FileHeader();
 | 
						|
			Header.Read(brROFst);
 | 
						|
			brROFst.BaseStream.Seek(Header.dboffset,SeekOrigin.Begin);
 | 
						|
			uint howbig = brROFst.ReadUInt32();
 | 
						|
			short howmany = brROFst.ReadInt16();
 | 
						|
 | 
						|
			numDatabases = howmany;
 | 
						|
			//			dbcount = numDatabases;
 | 
						|
			DatabasesInfo = new ArrayList();
 | 
						|
			dbiNewInfo = new ArrayList();
 | 
						|
 | 
						|
			// Load the database into the arrays
 | 
						|
			for (int i=0;i<numDatabases;i++)
 | 
						|
			{
 | 
						|
				dbinew dbinewItem;
 | 
						|
				ROFST_DbInfo tmpDBinfo;
 | 
						|
				tmpDBinfo = new ROFST_DbInfo();
 | 
						|
				tmpDBinfo.Load(brROFst);
 | 
						|
				DatabasesInfo.Add(tmpDBinfo);
 | 
						|
				dbinewItem = new dbinew();
 | 
						|
				dbiNewInfo.Add(dbinewItem);
 | 
						|
			}
 | 
						|
			for (int i=0;i<numDatabases;i++)
 | 
						|
			{
 | 
						|
				// load the titles and accessory page ids
 | 
						|
				//				((ROFST_DbInfo)DatabasesInfo[i]).ReadStrings(brROFst);
 | 
						|
				((ROFST_DbInfo)DatabasesInfo[i]).dbiTitle = GetAsciiString(brROFst);
 | 
						|
				((ROFST_DbInfo)DatabasesInfo[i]).dbiAP = GetAsciiString(brROFst);
 | 
						|
			}
 | 
						|
			// get the default graphic file extension
 | 
						|
			GetDefaultGraphicFileExtension();
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		~ ROFST_File()
 | 
						|
		{
 | 
						|
			if (brROFst!=null)brROFst.Close();
 | 
						|
		}
 | 
						|
 | 
						|
		public void Close()
 | 
						|
		{
 | 
						|
			if (brROFst!=null)brROFst.Close();
 | 
						|
			brROFst=null;
 | 
						|
		}
 | 
						|
		
 | 
						|
		private void GetDefaultGraphicFileExtension()
 | 
						|
		{
 | 
						|
			// get the full path to the VEPROMS.INI file
 | 
						|
			string ApplicationPath = Application.StartupPath;
 | 
						|
			string ApplPathUp = ApplicationPath.ToUpper();
 | 
						|
			int idx = ApplPathUp.IndexOf("VE-PROMS.NET\\BIN");
 | 
						|
			string PromsINI = ApplicationPath.Substring(0,idx);
 | 
						|
			PromsINI += "VE-PROMS\\VEPROMS.INI";
 | 
						|
 | 
						|
			PrivateProfile extINI = new PrivateProfile(PromsINI);
 | 
						|
			string defGrExt=extINI.Attr("Graphics", "defaultext");
 | 
						|
			if (defGrExt == null || defGrExt == "") 
 | 
						|
			{
 | 
						|
				// check the ROAPP.INI in the RO directory 
 | 
						|
				string ropath = extINI.Attr("RO Defaults","ROPATH");
 | 
						|
				if (ropath == null || ropath == "") ropath = "..\\RO";
 | 
						|
				string src = ropath + "\\ROAPP.INI";
 | 
						|
				if (File.Exists(src))
 | 
						|
				{
 | 
						|
					PrivateProfile roappINI = new PrivateProfile(src);
 | 
						|
					defGrExt = roappINI.Attr("ROApp","Extention");
 | 
						|
				}
 | 
						|
				if (defGrExt == null || defGrExt == "")
 | 
						|
					defGrExt="TIF";
 | 
						|
			}
 | 
						|
			DefaultGraphicFileExt = defGrExt;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Find the location of an RO value in the RO.FST file
 | 
						|
		private uint FindRO(uint id, uint start, uint end)
 | 
						|
		{
 | 
						|
			uint retval=0;
 | 
						|
			uint topid=0,botid=0,recs=0,siz=0;
 | 
						|
			siz=8;   // c code:sizeof(topid)*2;
 | 
						|
			recs=(end-start)/siz;
 | 
						|
			uint guessr,guess=0,guessid=0;
 | 
						|
			uint botr=0,topr=recs;
 | 
						|
			//getID(end-siz,&topoff);
 | 
						|
			brROFst.BaseStream.Seek(end-siz,SeekOrigin.Begin);
 | 
						|
			topid=brROFst.ReadUInt32(); 
 | 
						|
 | 
						|
			if(id==topid)return end-siz; // Last record
 | 
						|
 | 
						|
			//getID(start,&botoff);
 | 
						|
			brROFst.BaseStream.Seek(start,SeekOrigin.Begin);
 | 
						|
			botid=brROFst.ReadUInt32();
 | 
						|
 | 
						|
			if(id==botid)return start; // First record
 | 
						|
 | 
						|
			if(id < botid || id > topid)return 0; // Beyond range
 | 
						|
			while (topr > botr+1)
 | 
						|
			{
 | 
						|
				guessr=botr+((topr-botr)*(id-botid))/(topid-botid);
 | 
						|
 | 
						|
				if (guessr==botr) guessr=botr+1;
 | 
						|
				else if (guessr==topr) guessr=topr-1;
 | 
						|
 | 
						|
				guess=start+guessr*siz;
 | 
						|
				brROFst.BaseStream.Seek(guess,SeekOrigin.Begin);
 | 
						|
				//getID(guess,&retval)
 | 
						|
				guessid=brROFst.ReadUInt32();
 | 
						|
 | 
						|
				if(guessid==id)
 | 
						|
				{
 | 
						|
					break; // found, break out of while loop
 | 
						|
				} 
 | 
						|
				else if(guessid < id) 
 | 
						|
				{
 | 
						|
					botr=guessr;
 | 
						|
					botid=guessid;
 | 
						|
				} 
 | 
						|
				else 
 | 
						|
				{
 | 
						|
					topr=guessr;
 | 
						|
					topid=guessid;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			if(guessid==id)retval=guess;  // Any other record
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
		private uint _getID(uint off,ref uint nxtoff)
 | 
						|
		{
 | 
						|
			uint retval = 0;
 | 
						|
			if (off > 0)
 | 
						|
			{
 | 
						|
				brROFst.BaseStream.Seek(off,SeekOrigin.Begin);
 | 
						|
				retval = brROFst.ReadUInt32();
 | 
						|
				nxtoff = brROFst.ReadUInt32();
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
		// Find the location of an RO value in the RO.FST file
 | 
						|
		private uint toolsFindRO(uint id, uint start, uint end)
 | 
						|
		{
 | 
						|
			uint retval=0;
 | 
						|
			uint topid=0,botid=0,recs=0,siz=0;
 | 
						|
			siz=8;   // c code:sizeof(topid)*2;
 | 
						|
			recs=(end-start)/siz; //c code: (end-start)>>3
 | 
						|
			uint guessr,guess=0,guessid=0;
 | 
						|
			uint botr=0,topr=recs;
 | 
						|
			uint topoff =0, botoff=0;
 | 
						|
			//getID(end-siz,&topoff);
 | 
						|
			topid=_getID(end-siz,ref topoff);
 | 
						|
			if(id==topid)return topoff; // Last record
 | 
						|
 | 
						|
			//getID(start,&botoff);
 | 
						|
			botid=_getID(start,ref botoff);
 | 
						|
			if(id==botid)return botoff; // First record
 | 
						|
 | 
						|
			if(id < botid || id > topid)return 0; // Beyond range
 | 
						|
			while (topr > botr+1)
 | 
						|
			{
 | 
						|
				guessr=botr+((topr-botr)/2);
 | 
						|
 | 
						|
				if (guessr==botr) guessr++;
 | 
						|
				else if (guessr==topr) guessr--;
 | 
						|
 | 
						|
				//getID(guess,&retval)
 | 
						|
				guessid=_getID(start+guessr*siz,ref retval);
 | 
						|
 | 
						|
				if(guessid==id)
 | 
						|
				{
 | 
						|
					break; // found, break out of while loop
 | 
						|
				} 
 | 
						|
				else if(guessid < id) 
 | 
						|
				{
 | 
						|
					botr=guessr;
 | 
						|
					botid=guessid;
 | 
						|
				} 
 | 
						|
				else 
 | 
						|
				{
 | 
						|
					topr=guessr;
 | 
						|
					topid=guessid;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			if (guessid == id) return retval;
 | 
						|
			return 0;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// return the type of the given RO
 | 
						|
		private ROTypes FindROType(uint rec, uint start, uint end)
 | 
						|
		{
 | 
						|
			short retval=0;
 | 
						|
			byte[] tbyte= new byte[100];
 | 
						|
			uint fnd;
 | 
						|
			if((fnd=FindRO(rec,start,end))>0)
 | 
						|
			{
 | 
						|
				uint offset=brROFst.ReadUInt32();
 | 
						|
				brROFst.BaseStream.Seek((long)offset,SeekOrigin.Begin);
 | 
						|
				uint guessid=brROFst.ReadUInt32();
 | 
						|
				uint parid=brROFst.ReadUInt32();
 | 
						|
				short count=brROFst.ReadInt16();
 | 
						|
				retval=brROFst.ReadInt16(); // RO Type
 | 
						|
			}
 | 
						|
			return (ROTypes)retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get the RO Type from the ROID
 | 
						|
		public ROTypes GetROType(string ROID)
 | 
						|
		{
 | 
						|
			// break up ROID into table and record
 | 
						|
			ushort tbl = System.Convert.ToUInt16(ROID.Substring(0,4),16);
 | 
						|
			uint rec = System.Convert.ToUInt32(ROID.Substring(4,8),16);
 | 
						|
			ushort opt=0;
 | 
						|
			if (ROID.Length>12) opt = System.Convert.ToUInt16(ROID.Substring(8,ROID.Length-12),16);
 | 
						|
			if (tbl==0xFFFF) 
 | 
						|
				return ROTypes.None;    // 0xFFFF is ro from proc.ini file
 | 
						|
			int num=0;
 | 
						|
			for (int i=0; i < numDatabases && ((ROFST_DbInfo)DatabasesInfo[i]).dbiID!=tbl;i++) num++;
 | 
						|
			if (num < numDatabases)
 | 
						|
			{
 | 
						|
				return FindROType(rec,((ROFST_DbInfo)DatabasesInfo[num]).dbiIL,((ROFST_DbInfo)DatabasesInfo[num]).dbiAL);
 | 
						|
			}
 | 
						|
			return ROTypes.None;
 | 
						|
		}
 | 
						|
 | 
						|
		
 | 
						|
		private string FindROText(uint id, uint start,uint end)
 | 
						|
		{
 | 
						|
			string retval=null;
 | 
						|
			uint fnd;
 | 
						|
			if((fnd=FindRO(id,start,end))>0)
 | 
						|
			{
 | 
						|
				uint offset=brROFst.ReadUInt32();
 | 
						|
				brROFst.BaseStream.Seek((long)offset,SeekOrigin.Begin);
 | 
						|
				uint guessid=brROFst.ReadUInt32();
 | 
						|
				uint parid=brROFst.ReadUInt32();
 | 
						|
				short count=brROFst.ReadInt16();
 | 
						|
				ushort typ=brROFst.ReadUInt16();
 | 
						|
				if (count<0)retval=GetAsciiString(brROFst);
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// return the RO defined in the PROC.INI file
 | 
						|
		// (master / slave logic)
 | 
						|
		private string roUnitValue(uint rec)
 | 
						|
		{
 | 
						|
			string buff="";
 | 
						|
			PrivateProfile proc_ini = new PrivateProfile("proc.ini");
 | 
						|
			for(int i=0; i < NumUnitVariables; i++)
 | 
						|
			{
 | 
						|
				if((i+1) == rec)
 | 
						|
				{
 | 
						|
					buff = proc_ini.Attr("Unit",UnitVariables[i+1]);
 | 
						|
					if (buff == null || buff.Equals(""))
 | 
						|
						buff = "{"+ UnitVariables[i+1] + "}";
 | 
						|
					break; // break out of for loop
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return buff;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		//
 | 
						|
		// this function will take the ro text value and see if
 | 
						|
		// a macro has been used.  If so it will perform the macro
 | 
						|
		// operation on the substring in the text value
 | 
						|
		//
 | 
						|
		// right now the only macro is @HSP(), where every space between
 | 
						|
		// the "(" and ")" will be replaced with a hardspace
 | 
						|
		//
 | 
						|
		public string processMacros(string rostring)
 | 
						|
		{
 | 
						|
			StringBuilder bldstr = new StringBuilder();
 | 
						|
			int cptr = -1;
 | 
						|
			int stptr = 0;
 | 
						|
			if( rostring == null ) return rostring;
 | 
						|
			while( (cptr = rostring.IndexOf("@HSP(",stptr)) != -1 ) 
 | 
						|
			{
 | 
						|
				bldstr.Append(rostring.Substring(0,cptr-stptr));
 | 
						|
				int cptr2 = rostring.IndexOf(")",cptr);
 | 
						|
				if (cptr2 != -1)
 | 
						|
				{
 | 
						|
					int numspaces = cptr2 - cptr - 5;
 | 
						|
					for (int i=0; i< numspaces; i++)
 | 
						|
						bldstr.Append("\xFF");
 | 
						|
					stptr = cptr2 + 1;
 | 
						|
				}
 | 
						|
				else
 | 
						|
				{
 | 
						|
					bldstr.Append(rostring.Substring(cptr,5));
 | 
						|
					stptr += 5;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			if (stptr < rostring.Length)
 | 
						|
				bldstr.Append(rostring.Substring(stptr));
 | 
						|
			return bldstr.ToString();
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
 | 
						|
		private string processROString(string rostr, short menuitem)
 | 
						|
		{
 | 
						|
			string newstr="";
 | 
						|
			strList2 strlst2 = new strList2(rostr);
 | 
						|
			strList strlst = new strList(strlst2.toText());
 | 
						|
			newstr = strlst.toText((int)menuitem);
 | 
						|
			
 | 
						|
			newstr = newstr.Replace("\\n","\n");
 | 
						|
			newstr = processMacros(newstr);
 | 
						|
			return newstr;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public string GetRO(string ROID)
 | 
						|
		{
 | 
						|
			return _GetRO(ROID,1);
 | 
						|
		}
 | 
						|
 | 
						|
		public string GetEntireRO(string ROID)
 | 
						|
		{
 | 
						|
			return _GetRO(ROID,0);
 | 
						|
		}
 | 
						|
 | 
						|
		public string GetRO(string ROID, string ProcNum)
 | 
						|
		{
 | 
						|
			ROProcessTools.ProcedureNumber = ProcNum;
 | 
						|
			return GetRO(ROID);
 | 
						|
		}
 | 
						|
 | 
						|
		public string GetEntireRO(string ROID, string ProcNum)
 | 
						|
		{
 | 
						|
			ROProcessTools.ProcedureNumber = ProcNum;
 | 
						|
			return GetEntireRO(ROID);
 | 
						|
		}
 | 
						|
 | 
						|
		// Get the RO value from the ROID
 | 
						|
		private string _GetRO(string ROID_in, short procopt)
 | 
						|
		{
 | 
						|
			string ROID = ROID_in;
 | 
						|
			if (ROID.Length == 12)
 | 
						|
				ROID = ROID + "0000";
 | 
						|
			ushort tbl = System.Convert.ToUInt16(ROID.Substring(0,4),16);
 | 
						|
			uint rec = System.Convert.ToUInt32(ROID.Substring(4,8),16);
 | 
						|
			ushort opt=0;
 | 
						|
			// clear graphics info
 | 
						|
			LocalGrfStats.Clear();
 | 
						|
			opt = System.Convert.ToUInt16(ROID.Substring(12,ROID.Length-12),16);
 | 
						|
 | 
						|
			if (tbl==0xFFFF)
 | 
						|
				return roUnitValue(rec); // RO in PROC.INI file
 | 
						|
 | 
						|
			int num=0;
 | 
						|
			for(int i=0; i < numDatabases && ((ROFST_DbInfo)DatabasesInfo[i]).dbiID!=tbl;i++) num++;
 | 
						|
 | 
						|
			string retval = null;
 | 
						|
			if(num < numDatabases)
 | 
						|
			{
 | 
						|
				retval=FindROText(rec,((ROFST_DbInfo)DatabasesInfo[num]).dbiIL,((ROFST_DbInfo)DatabasesInfo[num]).dbiAL);
 | 
						|
			}
 | 
						|
			if ((retval!=null&&retval!="") && (GetROType(ROID)==ROTypes.Figure))
 | 
						|
			{
 | 
						|
				// load graphic stats
 | 
						|
				StringBuilder sbtmp = new StringBuilder();
 | 
						|
				LocalGrfStats.Load(retval);
 | 
						|
				sbtmp.Append(LocalGrfStats.PixFileName);
 | 
						|
				sbtmp.Append("\n");
 | 
						|
				sbtmp.Append(LocalGrfStats.PixFileTime.ToString("x8"));
 | 
						|
				sbtmp.Append("\n");
 | 
						|
				sbtmp.Append(LocalGrfStats.PixFileHeight.ToString("x4"));
 | 
						|
				sbtmp.Append("\n");
 | 
						|
				sbtmp.Append(LocalGrfStats.PixFileWidth.ToString("x4"));
 | 
						|
				retval = sbtmp.ToString();
 | 
						|
				
 | 
						|
			}
 | 
						|
			if(retval!=null && retval.Length>0 && !(GetROType(ROID)==ROTypes.Figure))
 | 
						|
			{
 | 
						|
				retval = retval.Replace("\r","");
 | 
						|
				if (procopt!=0) 
 | 
						|
				{
 | 
						|
					string newstr = processROString(retval,(short)opt);
 | 
						|
					if (newstr!=null && !newstr.Equals(""))
 | 
						|
						retval = newstr;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get the RO's parent ID
 | 
						|
		private uint GetParent(uint rec, uint start,uint end,ref uint offset)
 | 
						|
		{
 | 
						|
			uint parid=0;
 | 
						|
			uint fnd;
 | 
						|
			if((fnd=FindRO(rec,start,end))>0)
 | 
						|
			{
 | 
						|
				offset=brROFst.ReadUInt32();
 | 
						|
				brROFst.BaseStream.Seek((long)offset,SeekOrigin.Begin);
 | 
						|
				uint guessid=brROFst.ReadUInt32();
 | 
						|
				parid=brROFst.ReadUInt32();
 | 
						|
			}
 | 
						|
			return parid;
 | 
						|
		}
 | 
						|
 
 | 
						|
 | 
						|
		// Get the RO's parent ID from the ROID
 | 
						|
		public uint GetROParent(string ROID)
 | 
						|
		{
 | 
						|
			ushort tbl = Convert.ToUInt16(ROID.Substring(0,4),16);
 | 
						|
			uint  rec = Convert.ToUInt32(ROID.Substring(4,8),16);
 | 
						|
			uint retval=0;
 | 
						|
			int indx=0;
 | 
						|
			for(int i=0; i < numDatabases && ((ROFST_DbInfo)DatabasesInfo[i]).dbiID!=tbl; i++) indx++; // position to the RO database
 | 
						|
 | 
						|
			if(indx < numDatabases)
 | 
						|
			{
 | 
						|
				uint offset=0;
 | 
						|
				retval=GetParent(rec,((ROFST_DbInfo)DatabasesInfo[indx]).dbiIL,((ROFST_DbInfo)DatabasesInfo[indx]).dbiAL,ref offset);
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get the group title
 | 
						|
		private string GetDescription(ushort tbl, uint rec)
 | 
						|
		{
 | 
						|
			string retval=null;
 | 
						|
			if(tbl==0xFFFF)
 | 
						|
			{
 | 
						|
				if(rec == 0)
 | 
						|
				{
 | 
						|
					retval="Unit Information";
 | 
						|
				} 
 | 
						|
				
 | 
						|
				else if (rec <= NumUnitVariables)
 | 
						|
				{
 | 
						|
					int irec = (int)rec;
 | 
						|
					retval=UnitVariables[irec];
 | 
						|
				}				
 | 
						|
			} 
 | 
						|
			else 
 | 
						|
			{
 | 
						|
				int indx=0;
 | 
						|
				for(int i=0; i < numDatabases && ((ROFST_DbInfo)DatabasesInfo[i]).dbiID!=tbl; i++) indx++;
 | 
						|
 | 
						|
				if(indx < numDatabases)
 | 
						|
				{
 | 
						|
					uint id;
 | 
						|
					brROFst.BaseStream.Seek(((ROFST_DbInfo)DatabasesInfo[indx]).dbiGL,SeekOrigin.Begin);
 | 
						|
					id = brROFst.ReadUInt32();
 | 
						|
 | 
						|
					if((rec==0) || rec==id)
 | 
						|
					{
 | 
						|
						retval=((ROFST_DbInfo)DatabasesInfo[indx]).dbiTitle;
 | 
						|
					} 
 | 
						|
					else 
 | 
						|
					{
 | 
						|
						uint offset=0;
 | 
						|
						uint parid = this.GetParent(rec,((ROFST_DbInfo)DatabasesInfo[indx]).dbiIL,((ROFST_DbInfo)DatabasesInfo[indx]).dbiAL,ref offset);
 | 
						|
						if(parid!=0)
 | 
						|
						{
 | 
						|
							uint t1 = FindRO(parid,((ROFST_DbInfo)DatabasesInfo[indx]).dbiIL,((ROFST_DbInfo)DatabasesInfo[indx]).dbiAL);
 | 
						|
							t1 = brROFst.ReadUInt32();
 | 
						|
							uint guessid;
 | 
						|
							brROFst.BaseStream.Seek(t1,SeekOrigin.Begin);
 | 
						|
							guessid = brROFst.ReadUInt32();
 | 
						|
							parid = brROFst.ReadUInt32();
 | 
						|
							short count;
 | 
						|
							count = brROFst.ReadInt16();
 | 
						|
							for(int i=0; i < count && retval == null; i++)
 | 
						|
							{
 | 
						|
								uint off;
 | 
						|
								off=brROFst.ReadUInt32();
 | 
						|
								ushort typ;
 | 
						|
								typ=brROFst.ReadUInt16();
 | 
						|
								if(off==offset)
 | 
						|
								{
 | 
						|
									retval = GetAsciiString(brROFst);
 | 
						|
								} 
 | 
						|
								else 
 | 
						|
								{
 | 
						|
									SkipString(brROFst);
 | 
						|
								}
 | 
						|
							}
 | 
						|
						}
 | 
						|
					}
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get the group title by ROID
 | 
						|
		public string GetRODescription(string ROID)
 | 
						|
		{
 | 
						|
			ushort tbl = Convert.ToUInt16(ROID.Substring(0,4),16);
 | 
						|
			uint rec = Convert.ToUInt32(ROID.Substring(4,8),16);
 | 
						|
			return (GetDescription(tbl,rec));
 | 
						|
		}
 | 
						|
 | 
						|
		
 | 
						|
		// get the Accessory Page ID
 | 
						|
		string FindROAccID(uint id, uint start, uint end)
 | 
						|
		{
 | 
						|
			// Returns allocated space
 | 
						|
			string retval=null;
 | 
						|
			if(FindRO(id,start,end)!=0)
 | 
						|
			{
 | 
						|
				uint offset = brROFst.ReadUInt32();
 | 
						|
				brROFst.BaseStream.Seek(offset,SeekOrigin.Begin);
 | 
						|
				uint guessid = brROFst.ReadUInt32();
 | 
						|
				uint parid = brROFst.ReadUInt32();
 | 
						|
				short count = brROFst.ReadInt16();
 | 
						|
				ushort ltyp = brROFst.ReadUInt16();
 | 
						|
				SkipString(brROFst);
 | 
						|
				retval = GetAsciiString(brROFst);
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private string roUnitAccID(uint rec)
 | 
						|
		{
 | 
						|
			string rotbuf="";
 | 
						|
			for(int i=0; i < NumUnitVariables; i++)
 | 
						|
			{
 | 
						|
				if((i+1L)==rec)
 | 
						|
				{
 | 
						|
					rotbuf = "U-"+UnitVariables[i+1];
 | 
						|
					break; // break out of for loop
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return rotbuf;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get accessory page ID via the table and record
 | 
						|
		// also include unit specs from ini file
 | 
						|
		private string GetAccID(ushort tbl, uint rec)
 | 
						|
		{
 | 
						|
			string retval=null;
 | 
						|
 | 
						|
			if (tbl==0xFFFF)
 | 
						|
			{
 | 
						|
				return roUnitAccID(rec); // PROC.INI ro
 | 
						|
			}
 | 
						|
			int indx=0;
 | 
						|
			for(int i=0; i < numDatabases && ((ROFST_DbInfo)DatabasesInfo[i]).dbiID!=tbl; i++)indx++;
 | 
						|
 | 
						|
			if(indx < numDatabases)
 | 
						|
			{
 | 
						|
				retval=FindROAccID(rec,((ROFST_DbInfo)DatabasesInfo[indx]).dbiIL,((ROFST_DbInfo)DatabasesInfo[indx]).dbiAL);
 | 
						|
				if (retval ==  null)
 | 
						|
					retval="";	// RO not found, has ? in procedures
 | 
						|
				else
 | 
						|
					retval = ((ROFST_DbInfo)DatabasesInfo[indx]).dbiAP + "-" + retval;
 | 
						|
			}
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get the accessory page ID from the ROID
 | 
						|
		// includes unit specs from ini file
 | 
						|
		public string RoidToAccId(string ROID)
 | 
						|
		{
 | 
						|
			ushort tbl = Convert.ToUInt16(ROID.Substring(0,4),16);
 | 
						|
			uint rec = Convert.ToUInt32(ROID.Substring(4,8),16);
 | 
						|
			if(tbl != 0)
 | 
						|
				return GetAccID(tbl,rec);
 | 
						|
			return null;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get the accessory page ID
 | 
						|
		private string GetAppID(ushort tbl)
 | 
						|
		{
 | 
						|
			string retval = null;
 | 
						|
			if (tbl==0xFFFF)
 | 
						|
			{
 | 
						|
				return "U"; // PROC.INI ro
 | 
						|
			}
 | 
						|
			int indx=0;
 | 
						|
			for(int i=0; i < numDatabases && ((ROFST_DbInfo)DatabasesInfo[i]).dbiID!=tbl; i++) indx++;
 | 
						|
 | 
						|
			if(indx < numDatabases) 
 | 
						|
				return ((ROFST_DbInfo)DatabasesInfo[indx]).dbiAP;
 | 
						|
			return retval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Get the accessory page ID from the ROID
 | 
						|
		public string GetROAppID(string ROID)
 | 
						|
		{
 | 
						|
			ushort tbl = Convert.ToUInt16(ROID.Substring(0,4),16);
 | 
						|
			uint rec = Convert.ToUInt32(ROID.Substring(4,8),16);
 | 
						|
			return GetAppID(tbl);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public uint FindROFromTblRec(ushort tbl, uint id)
 | 
						|
		{
 | 
						|
			if(tbl==0xFFFF)
 | 
						|
			{
 | 
						|
				//PROC.INI ro
 | 
						|
				if (id < NumUnitVariables) return 1;
 | 
						|
				return 0;
 | 
						|
			}
 | 
						|
			int indx=0;
 | 
						|
			for(int i=0; i < numDatabases && ((ROFST_DbInfo)DatabasesInfo[i]).dbiID!=tbl;i++) indx++;
 | 
						|
			if (indx==numDatabases) return 0;
 | 
						|
			return FindRO(id,((ROFST_DbInfo)DatabasesInfo[indx]).dbiIL,((ROFST_DbInfo)DatabasesInfo[indx]).dbiAL);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public bool ROExists(string ROID)
 | 
						|
		{
 | 
						|
			ushort tbl = Convert.ToUInt16(ROID.Substring(0,4),16);
 | 
						|
			uint rec = Convert.ToUInt32(ROID.Substring(4,8),16);
 | 
						|
			uint off = FindROFromTblRec(tbl,rec);
 | 
						|
			return (off!=0);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public static void SkipString(BinaryReader br)
 | 
						|
		{
 | 
						|
			byte []input = {0};
 | 
						|
			do
 | 
						|
			{
 | 
						|
				try
 | 
						|
				{
 | 
						|
					input[0] = br.ReadByte();
 | 
						|
				}
 | 
						|
				catch (System.IO.EndOfStreamException)
 | 
						|
				{
 | 
						|
					input[0] = 0;
 | 
						|
				}
 | 
						|
			}while (input[0] != 0);
 | 
						|
			return;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public static string GetAsciiString(BinaryReader br, int len)
 | 
						|
		{
 | 
						|
			StringBuilder inpstr = new StringBuilder();
 | 
						|
			byte input = 0;
 | 
						|
			int cnt = 0;
 | 
						|
			do
 | 
						|
			{
 | 
						|
				try
 | 
						|
				{
 | 
						|
					input = br.ReadByte();
 | 
						|
					inpstr.Append(Convert.ToChar(input));
 | 
						|
				}
 | 
						|
				catch (System.IO.EndOfStreamException)
 | 
						|
				{
 | 
						|
					input = 0;
 | 
						|
					while (cnt < len)
 | 
						|
					{
 | 
						|
						inpstr.Append(Convert.ToChar(input));
 | 
						|
						cnt++;
 | 
						|
					}
 | 
						|
				}
 | 
						|
				cnt++;
 | 
						|
			}while (cnt < len);
 | 
						|
 | 
						|
			return (inpstr.ToString());
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public static string GetAsciiString(BinaryReader br)
 | 
						|
		{
 | 
						|
			StringBuilder inpstr = new StringBuilder();
 | 
						|
			byte input = 0;
 | 
						|
			do
 | 
						|
			{
 | 
						|
				try
 | 
						|
				{
 | 
						|
					input = br.ReadByte();
 | 
						|
					if (input > 0)
 | 
						|
					{
 | 
						|
						inpstr.Append(Convert.ToChar(input));
 | 
						|
					}
 | 
						|
				}
 | 
						|
				catch (System.IO.EndOfStreamException)
 | 
						|
				{
 | 
						|
					input = 0;
 | 
						|
				}
 | 
						|
			}while (input != 0);
 | 
						|
			return (inpstr.ToString());
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// return the index into the the DatabasesInfo array
 | 
						|
		private short GetTable(ushort tblid)
 | 
						|
		{
 | 
						|
			short found = -1;
 | 
						|
			for(short i = 0; (i < numDatabases) && (found == -1); i++)
 | 
						|
			{
 | 
						|
				if (tblid == ((ROFST_DbInfo)DatabasesInfo[i]).dbiID) 
 | 
						|
					found = i;
 | 
						|
			}
 | 
						|
 | 
						|
			if (found == -1)
 | 
						|
			{
 | 
						|
				// add a new item to the list
 | 
						|
				found = numDatabases;
 | 
						|
				ROFST_DbInfo tmpDbInfo = new ROFST_DbInfo();
 | 
						|
				tmpDbInfo.dbiID = tblid;
 | 
						|
				DatabasesInfo.Add(tmpDbInfo);
 | 
						|
				dbinew dbinewItem;
 | 
						|
				dbinewItem = new dbinew();
 | 
						|
				dbiNewInfo.Add(dbinewItem);
 | 
						|
				numDatabases++;
 | 
						|
			}
 | 
						|
			return found;
 | 
						|
		}
 | 
						|
		
 | 
						|
 | 
						|
		// Add a new RO record to the arraylist of allNewRos
 | 
						|
		private int AddNewRO(uint id,string num,string desc,string val,short type,uint grpn)
 | 
						|
		{
 | 
						|
			int rtval;
 | 
						|
			AddRO tmpAddRO = new AddRO();
 | 
						|
			tmpAddRO.ro_id = id;
 | 
						|
			tmpAddRO.ro_num = num;
 | 
						|
			tmpAddRO.ro_desc = desc;
 | 
						|
			tmpAddRO.ro_val = val;
 | 
						|
			tmpAddRO.ro_type = type;
 | 
						|
			tmpAddRO.ro_parid = grpn;
 | 
						|
			(allNewRos[curTblIdx]).Add(tmpAddRO);
 | 
						|
			rtval = (allNewRos[curTblIdx]).Count -1;
 | 
						|
			return rtval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private int AddNewRO(string num,string desc,string val,short type,uint grpn)
 | 
						|
		{
 | 
						|
			return AddNewRO(NewID++, num, desc, val, type, grpn);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Add a new Group record to the arraylist of allNewGrps
 | 
						|
		private int AddNewGroup(uint id,string grpname,short type)
 | 
						|
		{
 | 
						|
			int rtval;
 | 
						|
			AddGroup tmpAddGroup = new AddGroup();
 | 
						|
			tmpAddGroup.grp_id = id;
 | 
						|
			tmpAddGroup.grp_name = grpname;
 | 
						|
			tmpAddGroup.grp_type = type;
 | 
						|
			(allNewGrps[curTblIdx]).Add(tmpAddGroup);
 | 
						|
			rtval = (allNewGrps[curTblIdx]).Count -1;
 | 
						|
			return rtval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private int AddNewGroup(string grpname,short type)
 | 
						|
		{
 | 
						|
			return AddNewGroup(NewID++,grpname,type);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// Return the index into the allNewGrps arraylist
 | 
						|
		private int FindNewGroup(uint rec)
 | 
						|
		{
 | 
						|
			int rtval = -1;
 | 
						|
			for (int i=0; i < (allNewGrps[curTblIdx]).Count && rtval == -1; i++)
 | 
						|
			{
 | 
						|
				if (((AddGroup)(allNewGrps[curTblIdx])[i]).grp_id == rec)
 | 
						|
					rtval = i;
 | 
						|
			}
 | 
						|
			return rtval;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private int connectToNewGroupfRO(int lastaddROIDX,uint rec,uint parid,string desc)
 | 
						|
		{
 | 
						|
			int newgrpIDX;
 | 
						|
			// position to the correct RO group
 | 
						|
			if((newgrpIDX=FindNewGroup(rec))== -1)
 | 
						|
			{
 | 
						|
				// group not found, add a new one
 | 
						|
				newgrpIDX=AddNewGroup(rec,desc,0);
 | 
						|
			}
 | 
						|
			//update parent info
 | 
						|
			AddRO taddro = (AddRO)(allNewRos[curTblIdx][lastaddROIDX]);
 | 
						|
			taddro.ro_pargrpidx = newgrpIDX;
 | 
						|
			taddro.ro_parid = rec;
 | 
						|
			allNewRos[curTblIdx].RemoveAt(lastaddROIDX);
 | 
						|
			allNewRos[curTblIdx].Insert(lastaddROIDX,taddro);
 | 
						|
 | 
						|
			//update group info
 | 
						|
			AddGroup taddgroup = (AddGroup)(allNewGrps[curTblIdx][newgrpIDX]);
 | 
						|
			taddgroup.grp_type |= ((AddRO)(allNewRos[curTblIdx])[lastaddROIDX]).ro_type;
 | 
						|
			taddgroup.grp_parid = parid;
 | 
						|
			allNewGrps[curTblIdx].RemoveAt(newgrpIDX);
 | 
						|
			allNewGrps[curTblIdx].Insert(newgrpIDX,taddgroup);
 | 
						|
			return newgrpIDX;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private int connectToNewGroup(int lastaddgrpIDX,uint rec,uint parid,string desc)
 | 
						|
		{
 | 
						|
			// update group info
 | 
						|
			int newgrpIDX;
 | 
						|
			// position to the correct RO group
 | 
						|
			if((newgrpIDX=FindNewGroup(rec))== -1)
 | 
						|
			{
 | 
						|
				// group not found, add a new one
 | 
						|
				newgrpIDX=AddNewGroup(rec,desc,0);
 | 
						|
			}
 | 
						|
			AddGroup taddgroup = (AddGroup)(allNewGrps[curTblIdx][lastaddgrpIDX]);
 | 
						|
			taddgroup.grp_pargrpidx = newgrpIDX;
 | 
						|
			taddgroup.grp_parid = rec;
 | 
						|
			allNewGrps[curTblIdx].RemoveAt(lastaddgrpIDX);
 | 
						|
			allNewGrps[curTblIdx].Insert(lastaddgrpIDX,taddgroup);
 | 
						|
 | 
						|
			taddgroup = (AddGroup)(allNewGrps[curTblIdx][newgrpIDX]);
 | 
						|
			taddgroup.grp_type |= ((AddGroup)(allNewGrps[curTblIdx])[lastaddgrpIDX]).grp_type;
 | 
						|
			taddgroup.grp_parid = parid;
 | 
						|
			allNewGrps[curTblIdx].RemoveAt(newgrpIDX);
 | 
						|
			allNewGrps[curTblIdx].Insert(newgrpIDX,taddgroup);
 | 
						|
			return newgrpIDX;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private void addDifference(uint id,string val,string desc,short type,uint offset)
 | 
						|
		{
 | 
						|
			DiffRO tmpDiff  = new DiffRO();
 | 
						|
			tmpDiff.id=id;
 | 
						|
			tmpDiff.type=type;
 | 
						|
			tmpDiff.desc=desc;
 | 
						|
			tmpDiff.val=val;
 | 
						|
			tmpDiff.oldoff=offset;
 | 
						|
			allDifferences[curTblIdx].Add(tmpDiff);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private short ReadShort(BinaryReader br)
 | 
						|
		{
 | 
						|
			short rtnval = -1;
 | 
						|
			try
 | 
						|
			{
 | 
						|
				rtnval = br.ReadInt16();
 | 
						|
			}
 | 
						|
			catch (Exception)
 | 
						|
			{
 | 
						|
				rtnval = -1;
 | 
						|
			}
 | 
						|
			return rtnval;
 | 
						|
		}
 | 
						|
 | 
						|
/*
 | 
						|
 * Read in the ROFST Update file.  Put the changes in array lists
 | 
						|
 * to that will be used to organize and merge the differences into
 | 
						|
 * the target RO.FST file (usually in the Approved directory). For
 | 
						|
 * array lists, use the number of databases from the working draft
 | 
						|
 * (there may be new databases created since last approval)
 | 
						|
 */
 | 
						|
		public void processAppUpdFile(string sAppUpdFile, short nDB)
 | 
						|
		{
 | 
						|
			BinaryReader brAppUpd;
 | 
						|
			string num, desc, val;
 | 
						|
			short typ, inch;
 | 
						|
			uint rec;
 | 
						|
			ushort tbl;
 | 
						|
			uint parid;
 | 
						|
			int LastAddedROIDX=-1, LastAddedGrpIDX=-1;
 | 
						|
			curTblIdx = 0; // initialize Current Table Index
 | 
						|
			allNewRos = (ArrayList [])new ArrayList[nDB];
 | 
						|
			allNewGrps = (ArrayList [])new ArrayList[nDB];
 | 
						|
			allDifferences = (ArrayList [])new ArrayList[nDB];
 | 
						|
			allLocations = new ArrayList();
 | 
						|
 | 
						|
			for (int i=0; i<nDB; i++)
 | 
						|
			{
 | 
						|
				allNewRos[i] = new ArrayList();
 | 
						|
				allNewGrps[i] = new ArrayList();
 | 
						|
				allDifferences[i] = new ArrayList();
 | 
						|
			}
 | 
						|
			// Initialize the allLocations array
 | 
						|
			locinc tmplocinc = new locinc();
 | 
						|
			tmplocinc.inc = 0;
 | 
						|
			tmplocinc.maxloc = 0xFFFFFFFF;
 | 
						|
			allLocations.Add(tmplocinc);
 | 
						|
 | 
						|
			// Open the AppUpd file and read in the RO.FST changes
 | 
						|
			try
 | 
						|
			{
 | 
						|
				brAppUpd = new BinaryReader(File.Open(sAppUpdFile,System.IO.FileMode.Open,System.IO.FileAccess.Read,FileShare.Read));
 | 
						|
			}
 | 
						|
			catch (Exception e)
 | 
						|
			{
 | 
						|
				MessageBox.Show("Open "+sAppUpdFile+"\n\n" + e.Message,"Approval Error");
 | 
						|
				return;
 | 
						|
			}
 | 
						|
 | 
						|
			while ((inch = ReadShort(brAppUpd)) != -1)
 | 
						|
			{
 | 
						|
				if (inch == 0 || inch == 1)
 | 
						|
				{
 | 
						|
					// Read the ROID for the Table and Record Number
 | 
						|
					tbl = brAppUpd.ReadUInt16(); // table number
 | 
						|
					rec = brAppUpd.ReadUInt32(); // RO Record number
 | 
						|
 | 
						|
					// Position to the correct RO database
 | 
						|
					// ex. Setpoint, Graphics, User Defined, etc.
 | 
						|
					curTblIdx = GetTable(tbl);
 | 
						|
 | 
						|
					// Read in the RO FST record information
 | 
						|
					parid = brAppUpd.ReadUInt32(); // Parid
 | 
						|
					typ = brAppUpd.ReadInt16();	// type
 | 
						|
					desc = GetAsciiString(brAppUpd); // description
 | 
						|
					val = GetAsciiString(brAppUpd); // value
 | 
						|
					num = GetAsciiString(brAppUpd); // acc ID
 | 
						|
					if (inch==0) 
 | 
						|
						// New RO FST record
 | 
						|
						LastAddedROIDX = AddNewRO(rec,num,desc,val,typ,parid);
 | 
						|
					else
 | 
						|
					{
 | 
						|
						// Find existing RO FST record in Approved RO.FST
 | 
						|
						uint start = ((ROFST_DbInfo)DatabasesInfo[curTblIdx]).dbiIL;
 | 
						|
						uint end = ((ROFST_DbInfo)DatabasesInfo[curTblIdx]).dbiAL;
 | 
						|
						//NOTE: the FindRO() used in the old rofstupd.c code
 | 
						|
						// had some differences, but we will try the following
 | 
						|
						// version of this function since its logic appears in 
 | 
						|
						// other areas of VE-PROMS code.
 | 
						|
						uint OldOff = toolsFindRO(rec,start,end);
 | 
						|
						// Save the differences
 | 
						|
						addDifference(rec,val,desc,typ,OldOff);
 | 
						|
					}
 | 
						|
				} 
 | 
						|
				else
 | 
						|
				{
 | 
						|
					rec = brAppUpd.ReadUInt32(); // RO Record number
 | 
						|
					parid = brAppUpd.ReadUInt32();
 | 
						|
					desc = GetAsciiString(brAppUpd);
 | 
						|
					if (parid == 0)
 | 
						|
					{
 | 
						|
						string apid= GetAsciiString(brAppUpd);
 | 
						|
						((ROFST_DbInfo)DatabasesInfo[curTblIdx]).dbiTitle = desc;
 | 
						|
						((ROFST_DbInfo)DatabasesInfo[curTblIdx]).dbiAP = apid;
 | 
						|
					}
 | 
						|
					if (LastAddedROIDX != -1)
 | 
						|
						// update value in allNewRos
 | 
						|
						LastAddedGrpIDX = connectToNewGroupfRO(LastAddedROIDX,rec,parid,desc);
 | 
						|
					else
 | 
						|
						// update value in allNewGrps
 | 
						|
						LastAddedGrpIDX = connectToNewGroup(LastAddedGrpIDX,rec,parid,desc);
 | 
						|
					LastAddedROIDX = -1;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			brAppUpd.Close();
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// format strings used in the RO.FST menus that are displayed
 | 
						|
		// in the VE-PROMS Editor
 | 
						|
		private void placeText(StringBuilder buff,ushort doff,ushort wid,string instr)
 | 
						|
		{
 | 
						|
			ushort siznum=0;
 | 
						|
			string str = instr;
 | 
						|
			int idx =0;
 | 
						|
			if(doff != 0)
 | 
						|
			{
 | 
						|
				str = str.TrimStart(' '); // skip leading spaces
 | 
						|
				ushort l=(ushort)str.Length;
 | 
						|
				string numandsigns = "0123456789+-";
 | 
						|
				while (numandsigns.IndexOf(str[idx])!=-1)
 | 
						|
				{
 | 
						|
					siznum++;
 | 
						|
					idx++;
 | 
						|
				}
 | 
						|
				if(siznum==0)
 | 
						|
				{// doff is calculated to keep the values positive
 | 
						|
					doff=((ushort)(siznum+(wid-l)/2)); // if no digits - center
 | 
						|
				} 
 | 
						|
				else if(((doff-siznum)+l) > wid)
 | 
						|
				{
 | 
						|
					doff=(ushort)(wid-siznum-l);
 | 
						|
				}
 | 
						|
				while(wid > 0 && siznum < doff)
 | 
						|
				{ // add spaces if necessary for alignment
 | 
						|
					buff.Append(' ');
 | 
						|
					siznum++;
 | 
						|
					wid--;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			idx = 0;
 | 
						|
			while(wid > 0)
 | 
						|
			{ // output the value or spaces to the specified width
 | 
						|
				if (idx < str.Length && str[idx] != 0 && str[idx] != '\n')
 | 
						|
					buff.Append(str[idx]);
 | 
						|
				else
 | 
						|
					buff.Append(" ");
 | 
						|
				wid--;
 | 
						|
				idx++;
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		private string getMenuString(short type,string val,string desc)
 | 
						|
		{
 | 
						|
			StringBuilder buff = new StringBuilder();
 | 
						|
			switch(type)
 | 
						|
			{
 | 
						|
				case 1:
 | 
						|
					placeText(buff,5,17,val);
 | 
						|
					buff.Append(" ");
 | 
						|
					break;
 | 
						|
				case 2:
 | 
						|
					placeText(buff,5,17,"(Table)");
 | 
						|
					buff.Append(" ");
 | 
						|
					break;
 | 
						|
				case 4:
 | 
						|
					placeText(buff,5,17,"(Graph)");
 | 
						|
					buff.Append(" ");
 | 
						|
					break;
 | 
						|
			}
 | 
						|
			buff.Append(desc);
 | 
						|
			return buff.ToString();
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void WriteString(BinaryWriter NewFSTFile, string str,bool AddNull)
 | 
						|
		{
 | 
						|
			int n=str.Length;
 | 
						|
			if (AddNull) 
 | 
						|
				n++;
 | 
						|
			byte [] b = new byte[n];
 | 
						|
			for(int i =0; i < str.Length; i++)
 | 
						|
			{
 | 
						|
				b[i] = (byte)str[i];
 | 
						|
			}
 | 
						|
			NewFSTFile.Write(b,0,n);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public uint saveNewMenuEntries(BinaryWriter NewFSTFile,uint id)
 | 
						|
		{
 | 
						|
			long start=NewFSTFile.Seek(0,System.IO.SeekOrigin.Current);
 | 
						|
			int numNewRos = (allNewRos[curTblIdx]).Count;
 | 
						|
			int cntNewRos = 0;
 | 
						|
			while (cntNewRos < numNewRos)
 | 
						|
			{
 | 
						|
				// Skip to the one to be saved
 | 
						|
				while ((cntNewRos < numNewRos) &&
 | 
						|
					(((AddRO)(allNewRos[curTblIdx])[cntNewRos]).ro_stat != 1) &&
 | 
						|
					((AddRO)(allNewRos[curTblIdx])[cntNewRos]).ro_parid != id)
 | 
						|
					cntNewRos++;
 | 
						|
				// If one exists, save it and skip to the next one
 | 
						|
				if (cntNewRos < numNewRos)
 | 
						|
				{
 | 
						|
					AddRO taddro = (AddRO)(allNewRos[curTblIdx][cntNewRos]);
 | 
						|
					taddro.ro_stat = 2;
 | 
						|
					allNewRos[curTblIdx].RemoveAt(cntNewRos);
 | 
						|
					allNewRos[curTblIdx].Insert(cntNewRos,taddro);
 | 
						|
					// Save the offset
 | 
						|
					NewFSTFile.Write(((AddRO)(allNewRos[curTblIdx])[cntNewRos]).ro_offset);
 | 
						|
					// Save the type
 | 
						|
					NewFSTFile.Write(((AddRO)(allNewRos[curTblIdx])[cntNewRos]).ro_type);
 | 
						|
					// Get the menu string
 | 
						|
					string mnustr = getMenuString(((AddRO)(allNewRos[curTblIdx])[cntNewRos]).ro_type,((AddRO)(allNewRos[curTblIdx])[cntNewRos]).ro_val,((AddRO)(allNewRos[curTblIdx])[cntNewRos]).ro_desc);
 | 
						|
					// Save menu entry
 | 
						|
					WriteString(NewFSTFile,mnustr,true);
 | 
						|
					cntNewRos++;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			int cntNewGrps = 0;
 | 
						|
			int numNewGrps = (allNewGrps[curTblIdx]).Count;
 | 
						|
			while (cntNewGrps < numNewGrps)
 | 
						|
			{
 | 
						|
				// Skip to the one to be saved
 | 
						|
				while ((cntNewGrps < numNewGrps) &&
 | 
						|
					(((AddGroup)(allNewGrps[curTblIdx])[cntNewGrps]).grp_stat != 1 ||
 | 
						|
					((AddGroup)(allNewGrps[curTblIdx])[cntNewGrps]).grp_parid != id))
 | 
						|
					cntNewGrps++;
 | 
						|
				// If one exists, save it and skip to the next one
 | 
						|
				if(cntNewGrps < numNewGrps)
 | 
						|
				{
 | 
						|
					// Change stat to menu entry saved
 | 
						|
					AddGroup taddgroup = (AddGroup)(allNewGrps[curTblIdx][cntNewGrps]);
 | 
						|
					taddgroup.grp_stat = 2;
 | 
						|
					allNewGrps[curTblIdx].RemoveAt(cntNewGrps);
 | 
						|
					allNewGrps[curTblIdx].Insert(cntNewGrps,taddgroup);
 | 
						|
					// Save the offset
 | 
						|
					NewFSTFile.Write(((AddGroup)(allNewGrps[curTblIdx])[cntNewGrps]).grp_offset);
 | 
						|
					// Save the type
 | 
						|
					NewFSTFile.Write(((AddGroup)(allNewGrps[curTblIdx])[cntNewGrps]).grp_type);
 | 
						|
					// Save menu entry
 | 
						|
					WriteString(NewFSTFile,((AddGroup)(allNewGrps[curTblIdx])[cntNewGrps]).grp_name,true);
 | 
						|
					cntNewGrps++;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return ((uint)((NewFSTFile.Seek(0,System.IO.SeekOrigin.Current)) - start));
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
 | 
						|
		public void AddLocation(uint location,int inc)
 | 
						|
		{
 | 
						|
			int t_inc = ((locinc)allLocations[lastLocationIdx]).inc;
 | 
						|
			if (location == ((locinc)allLocations[lastLocationIdx]).maxloc)
 | 
						|
			{
 | 
						|
				// update the current record
 | 
						|
				// - need to remove current item, then insert new item.
 | 
						|
				locinc tmploc = (locinc)(allLocations[lastLocationIdx]);
 | 
						|
				tmploc.inc += inc;
 | 
						|
				allLocations.RemoveAt(lastLocationIdx);
 | 
						|
				allLocations.Insert(lastLocationIdx,tmploc);
 | 
						|
			}
 | 
						|
			else
 | 
						|
			{
 | 
						|
				locinc tmploc = (locinc)(allLocations[lastLocationIdx]);
 | 
						|
				locinc newloc = new locinc();
 | 
						|
				// new item gets last item's maxloc
 | 
						|
				newloc.maxloc = tmploc.maxloc;
 | 
						|
				newloc.inc = tmploc.inc + inc;
 | 
						|
				// update the current record
 | 
						|
				// - need to remove current item, then insert new item.
 | 
						|
				tmploc.maxloc = location; //update maxloc
 | 
						|
				allLocations.RemoveAt(lastLocationIdx);
 | 
						|
				allLocations.Insert(lastLocationIdx,tmploc);
 | 
						|
				// append the new item
 | 
						|
				allLocations.Add(newloc);
 | 
						|
				lastLocationIdx++;
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public short saveAdditions(BinaryWriter NewFSTFile,uint parid,uint start)
 | 
						|
		{
 | 
						|
			// Initialize count of added entries
 | 
						|
			short count = 0;
 | 
						|
			// Initialize count of added bytes
 | 
						|
			int bytes = 0;
 | 
						|
 | 
						|
			int numgroups = (allNewGrps[curTblIdx]).Count;
 | 
						|
			int grpcnt = 0;
 | 
						|
			while (grpcnt < numgroups)
 | 
						|
			{
 | 
						|
				if (((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_stat == 0 && ((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_parid == parid)
 | 
						|
				{
 | 
						|
					// Save new group
 | 
						|
					// Change stat to inprogress
 | 
						|
					AddGroup taddgroup = (AddGroup)(allNewGrps[curTblIdx][grpcnt]);
 | 
						|
					taddgroup.grp_stat = 99;
 | 
						|
					allNewGrps[curTblIdx].RemoveAt(grpcnt);
 | 
						|
					allNewGrps[curTblIdx].Insert(grpcnt,taddgroup);
 | 
						|
					count++;
 | 
						|
					// Save any children
 | 
						|
					short howmany = saveAdditions(NewFSTFile,((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_id,start);
 | 
						|
 | 
						|
					// Remember the offset
 | 
						|
					taddgroup = (AddGroup)(allNewGrps[curTblIdx][grpcnt]);
 | 
						|
					taddgroup.grp_offset = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current); // ftell(ofile)
 | 
						|
					allNewGrps[curTblIdx].RemoveAt(grpcnt);
 | 
						|
					allNewGrps[curTblIdx].Insert(grpcnt,taddgroup);
 | 
						|
 | 
						|
					// Save ID
 | 
						|
					if (((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_parid == 0)
 | 
						|
					{
 | 
						|
						whereisgl = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current);
 | 
						|
					}
 | 
						|
					NewFSTFile.Write(((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_id);
 | 
						|
					// Save the Parent ID
 | 
						|
					NewFSTFile.Write(((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_parid);
 | 
						|
					// save howmany
 | 
						|
					NewFSTFile.Write(howmany);
 | 
						|
					// save children
 | 
						|
					saveNewMenuEntries(NewFSTFile,((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_id);
 | 
						|
					taddgroup = (AddGroup)(allNewGrps[curTblIdx][grpcnt]);
 | 
						|
					taddgroup.grp_stat = 1;
 | 
						|
					allNewGrps[curTblIdx].RemoveAt(grpcnt);
 | 
						|
					allNewGrps[curTblIdx].Insert(grpcnt,taddgroup);
 | 
						|
					bytes += (int)(NewFSTFile.Seek(0,System.IO.SeekOrigin.Current) - ((AddGroup)(allNewGrps[curTblIdx])[grpcnt]).grp_offset);
 | 
						|
				}
 | 
						|
				grpcnt++;
 | 
						|
			}
 | 
						|
			// Second check new ROs
 | 
						|
			int rocnt = 0;
 | 
						|
			int numros = (allNewRos[curTblIdx]).Count;
 | 
						|
			while (rocnt < numros)
 | 
						|
			{
 | 
						|
				// save new RO
 | 
						|
				if (((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_stat == 0 &&
 | 
						|
					((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_parid == parid)
 | 
						|
				{
 | 
						|
					// change the stat
 | 
						|
					AddRO taddro = (AddRO)(allNewRos[curTblIdx][rocnt]);
 | 
						|
					taddro.ro_stat = 1;
 | 
						|
					// Increment count
 | 
						|
					count++;
 | 
						|
					taddro.ro_offset = (int)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current);
 | 
						|
					allNewRos[curTblIdx].RemoveAt(rocnt);
 | 
						|
					allNewRos[curTblIdx].Insert(rocnt,taddro);
 | 
						|
					// Save the ID
 | 
						|
					NewFSTFile.Write(((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_id);
 | 
						|
					// Save the Parent ID
 | 
						|
					NewFSTFile.Write(((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_parid);
 | 
						|
					// Save -1
 | 
						|
					NewFSTFile.Write((short)-1);
 | 
						|
					// Save type
 | 
						|
					NewFSTFile.Write(((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_type);
 | 
						|
					maxtype |= (ushort)((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_type;
 | 
						|
					// Save value
 | 
						|
					WriteString(NewFSTFile,((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_val,true);
 | 
						|
					// Save accid
 | 
						|
					short aw = (short)((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_num.Length;
 | 
						|
					if (aw > maxaw) maxaw = (ushort)aw;
 | 
						|
					WriteString(NewFSTFile,((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_num,true);
 | 
						|
					// Calculate the number of extra bytes output
 | 
						|
					bytes+=(int)(NewFSTFile.Seek(0,System.IO.SeekOrigin.Current) - ((AddRO)(allNewRos[curTblIdx])[rocnt]).ro_offset);
 | 
						|
				}
 | 
						|
				rocnt++;
 | 
						|
			}
 | 
						|
			// Adjust the location information
 | 
						|
			if (bytes != 0 && start > 0)
 | 
						|
				AddLocation(start - 1,bytes);
 | 
						|
			return count;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		// was a difference flagged for this RO
 | 
						|
		// - check via saved offsets into the RO.fST file
 | 
						|
		public int isDifferent(uint off)
 | 
						|
		{
 | 
						|
			int allDiffCnt = 0;
 | 
						|
			int NumAllDiff = (allDifferences[curTblIdx]).Count;
 | 
						|
			while (allDiffCnt < NumAllDiff)
 | 
						|
			{
 | 
						|
				if (((DiffRO)(allDifferences[curTblIdx])[allDiffCnt]).oldoff == off)
 | 
						|
					return allDiffCnt;
 | 
						|
				allDiffCnt++;
 | 
						|
			}
 | 
						|
			return -1;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
 | 
						|
		public uint newLocation(uint oldlocation)
 | 
						|
		{
 | 
						|
			int idx = 0;
 | 
						|
			while (oldlocation > ((locinc)allLocations[idx]).maxloc) idx++;
 | 
						|
			return oldlocation + (uint)((locinc)allLocations[idx]).inc;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void processGroupRecords(BinaryWriter NewFSTFile,uint end)
 | 
						|
		{
 | 
						|
			uint start;
 | 
						|
			while ((start=(uint)brROFst.BaseStream.Seek(0,System.IO.SeekOrigin.Current)) < end)
 | 
						|
			{
 | 
						|
				// Read ID
 | 
						|
				uint id = brROFst.ReadUInt32();
 | 
						|
				// Read Parent ID
 | 
						|
				uint parid = brROFst.ReadUInt32();
 | 
						|
				// Read How Many
 | 
						|
				short howmany = brROFst.ReadInt16();
 | 
						|
				// Check of additions and write them
 | 
						|
				short howmanyplus = howmany;
 | 
						|
				if (howmany >= 0)
 | 
						|
					howmanyplus += saveAdditions(NewFSTFile,id,start);
 | 
						|
				if (parid == 0)
 | 
						|
					whereisgl = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current); // ftell(ofile)
 | 
						|
				// Write ID
 | 
						|
				NewFSTFile.Write(id);
 | 
						|
				// Write Parent ID
 | 
						|
				NewFSTFile.Write(parid);
 | 
						|
				// Write howmany
 | 
						|
				NewFSTFile.Write(howmanyplus);
 | 
						|
				// If group - read and write menu list
 | 
						|
				int starti = (int)brROFst.BaseStream.Seek(0,System.IO.SeekOrigin.Current); // ftell(rofstfile)
 | 
						|
				int starto = (int)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current); // ftell(ofile)
 | 
						|
				if (howmanyplus >= 0)
 | 
						|
				{
 | 
						|
					// for orignal entries
 | 
						|
					for (int i=0;i<howmany;i++)
 | 
						|
					{
 | 
						|
						// Read Offset
 | 
						|
						uint offset = brROFst.ReadUInt32();
 | 
						|
						// Read Type
 | 
						|
						short type = brROFst.ReadInt16();
 | 
						|
						// Read Menu
 | 
						|
						string menustr = GetAsciiString(brROFst);
 | 
						|
						// Look for differences
 | 
						|
						int thisdiff = isDifferent(offset);
 | 
						|
						if (thisdiff != -1)
 | 
						|
						{
 | 
						|
							type = ((DiffRO)(allDifferences[curTblIdx])[thisdiff]).type;
 | 
						|
							menustr = getMenuString(type,((DiffRO)(allDifferences[curTblIdx])[thisdiff]).val,((DiffRO)(allDifferences[curTblIdx])[thisdiff]).desc);
 | 
						|
						}
 | 
						|
						// Save new offset
 | 
						|
						NewFSTFile.Write(newLocation(offset));
 | 
						|
						// Save type
 | 
						|
						NewFSTFile.Write(type);
 | 
						|
						// Save menu
 | 
						|
						WriteString(NewFSTFile,menustr,true);
 | 
						|
					}
 | 
						|
					// Save new entries
 | 
						|
					if (howmanyplus > howmany)
 | 
						|
					{
 | 
						|
						saveNewMenuEntries(NewFSTFile,id);
 | 
						|
					}
 | 
						|
				}
 | 
						|
				else
 | 
						|
				{
 | 
						|
					// if RO - read RO record
 | 
						|
					// Read type
 | 
						|
					short type = brROFst.ReadInt16();
 | 
						|
					// Read value
 | 
						|
					string val = GetAsciiString(brROFst);
 | 
						|
					// Read accid
 | 
						|
					string num = GetAsciiString(brROFst);
 | 
						|
					// check if changed
 | 
						|
					int thisdiff = isDifferent(start);
 | 
						|
					if (thisdiff != -1)
 | 
						|
					{
 | 
						|
						type = ((DiffRO)(allDifferences[curTblIdx])[thisdiff]).type;
 | 
						|
						val = ((DiffRO)(allDifferences[curTblIdx])[thisdiff]).val;
 | 
						|
					}
 | 
						|
					// Save type
 | 
						|
					NewFSTFile.Write(type);
 | 
						|
					// Save value
 | 
						|
					WriteString(NewFSTFile,val,true);
 | 
						|
					// Save accid
 | 
						|
					WriteString(NewFSTFile,num,true);
 | 
						|
				}
 | 
						|
				int originalSize = (int)brROFst.BaseStream.Seek(0,System.IO.SeekOrigin.Current) - starti;
 | 
						|
				int copySize = (int)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current) - starto;
 | 
						|
				if (copySize != originalSize)
 | 
						|
					AddLocation(start,copySize - originalSize);
 | 
						|
			}
 | 
						|
			if (end == 0)
 | 
						|
			{
 | 
						|
				maxtype = 0;
 | 
						|
				maxaw = 0;
 | 
						|
				saveAdditions(NewFSTFile,0,0);
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public int getROAccLess(string minnum)
 | 
						|
		{
 | 
						|
			int romin = -1;
 | 
						|
			int roptr = 0;
 | 
						|
			int numroptr = (allNewRos[curTblIdx]).Count;
 | 
						|
			while (roptr < numroptr)
 | 
						|
			{
 | 
						|
				// skip processed entries
 | 
						|
				while ((roptr < numroptr) &&
 | 
						|
					((AddRO)(allNewRos[curTblIdx])[roptr]).ro_stat == 4) roptr++;
 | 
						|
				if ((roptr < numroptr))
 | 
						|
				{
 | 
						|
					// Look for "smallest"
 | 
						|
					if ((minnum==null)||
 | 
						|
						((AddRO)(allNewRos[curTblIdx])[roptr]).ro_num.CompareTo(minnum) < 0)
 | 
						|
					{
 | 
						|
						romin = roptr;
 | 
						|
						minnum = ((AddRO)(allNewRos[curTblIdx])[roptr]).ro_num;
 | 
						|
					}
 | 
						|
					roptr++;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return romin;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void putFixed(BinaryWriter NewFstFile, string str, short len)
 | 
						|
		{
 | 
						|
			int n=len; //str.Length;
 | 
						|
			int strlen = str.Length;
 | 
						|
			byte [] b = new byte[len];
 | 
						|
		// write a fixed length of a string.
 | 
						|
			for (int i =0; n > 0; i++)
 | 
						|
			{
 | 
						|
				if (i < strlen)
 | 
						|
					b[i] = (byte)str[i];
 | 
						|
				else
 | 
						|
					b[i] = (byte)0; // pad with NULLs if smaller than "len"
 | 
						|
				n--;
 | 
						|
			}
 | 
						|
			NewFstFile.Write(b,0,len);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void processAccIdRecords(BinaryWriter NewFSTFile,uint end,short len)
 | 
						|
		{
 | 
						|
			int extra = 0;
 | 
						|
			int roptr = 0;
 | 
						|
			while (brROFst.BaseStream.Seek(0,System.IO.SeekOrigin.Current) < end)
 | 
						|
			{
 | 
						|
				// Read ID
 | 
						|
				uint id = brROFst.ReadUInt32();
 | 
						|
				// Read accID
 | 
						|
				string num = GetAsciiString(brROFst,len);
 | 
						|
				// Check other accIDs in new records and save
 | 
						|
				while ((roptr = getROAccLess(num)) != -1)
 | 
						|
				{
 | 
						|
					extra+=(len + 4); //sizeof(ulong 16bit)+len
 | 
						|
					NewFSTFile.Write(((AddRO)(allNewRos[curTblIdx])[roptr]).ro_id);
 | 
						|
					putFixed(NewFSTFile,((AddRO)(allNewRos[curTblIdx])[roptr]).ro_num,len);
 | 
						|
					AddRO taddro = (AddRO)(allNewRos[curTblIdx][roptr]);
 | 
						|
					taddro.ro_stat = 4;
 | 
						|
					allNewRos[curTblIdx].RemoveAt(roptr);
 | 
						|
					allNewRos[curTblIdx].Insert(roptr,taddro);
 | 
						|
				}
 | 
						|
				// Write ID
 | 
						|
				NewFSTFile.Write(id);
 | 
						|
				// Write accID
 | 
						|
				putFixed(NewFSTFile,num,len);
 | 
						|
			}
 | 
						|
			// Save remaining RO info
 | 
						|
			while ((roptr = getROAccLess(null))!=-1)
 | 
						|
			{
 | 
						|
				extra += (len+4); //sizeof(ulong 16bit)+len
 | 
						|
				NewFSTFile.Write(((AddRO)(allNewRos[curTblIdx])[roptr]).ro_id);
 | 
						|
				putFixed(NewFSTFile,((AddRO)(allNewRos[curTblIdx])[roptr]).ro_num,len);
 | 
						|
				AddRO taddro = (AddRO)(allNewRos[curTblIdx][roptr]);
 | 
						|
				taddro.ro_stat = 4;
 | 
						|
				allNewRos[curTblIdx].RemoveAt(roptr);
 | 
						|
				allNewRos[curTblIdx].Insert(roptr,taddro);
 | 
						|
			}
 | 
						|
			if (extra > 0) 
 | 
						|
				AddLocation(end-1,extra);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void nextIDandOffset(ref uint nxtid, ref uint nxtoff)
 | 
						|
		{
 | 
						|
			int roptr = 0, romin = -1;
 | 
						|
			int numroptr = (allNewRos[curTblIdx]).Count;
 | 
						|
			int grpptr = 0, grpmin = -1;
 | 
						|
			int numgrpptr = (allNewGrps[curTblIdx]).Count;
 | 
						|
 | 
						|
			while (roptr < numroptr)
 | 
						|
			{
 | 
						|
				if (((AddRO)(allNewRos[curTblIdx])[roptr]).ro_id > nxtid &&
 | 
						|
					(romin == -1 || ((AddRO)(allNewRos[curTblIdx])[roptr]).ro_id < ((AddRO)(allNewRos[curTblIdx])[romin]).ro_id))
 | 
						|
					romin = roptr;
 | 
						|
				roptr++;
 | 
						|
			}
 | 
						|
 | 
						|
			while (grpptr < numgrpptr)
 | 
						|
			{
 | 
						|
				if (((AddGroup)(allNewGrps[curTblIdx])[grpptr]).grp_id > nxtid &&
 | 
						|
					(grpmin == -1 || ((AddGroup)(allNewGrps[curTblIdx])[grpptr]).grp_id < ((AddGroup)(allNewGrps[curTblIdx])[grpmin]).grp_id))
 | 
						|
					grpmin = grpptr;
 | 
						|
				grpptr++;
 | 
						|
			}
 | 
						|
			if (grpmin != -1)
 | 
						|
			{
 | 
						|
				if ((romin != -1) && ((AddRO)(allNewRos[curTblIdx])[romin]).ro_id < ((AddGroup)(allNewGrps[curTblIdx])[grpmin]).grp_id)
 | 
						|
				{
 | 
						|
					AddRO taddro = (AddRO)(allNewRos[curTblIdx][romin]);
 | 
						|
					taddro.ro_stat = 3;
 | 
						|
					allNewRos[curTblIdx].RemoveAt(romin);
 | 
						|
					allNewRos[curTblIdx].Insert(romin,taddro);
 | 
						|
					nxtid = ((AddRO)(allNewRos[curTblIdx])[romin]).ro_id;
 | 
						|
					nxtoff = (uint)((AddRO)(allNewRos[curTblIdx])[romin]).ro_offset;
 | 
						|
				}
 | 
						|
				else
 | 
						|
				{
 | 
						|
					AddGroup taddgroup = (AddGroup)(allNewGrps[curTblIdx][grpmin]);
 | 
						|
					taddgroup.grp_stat = 3;
 | 
						|
					allNewGrps[curTblIdx].RemoveAt(grpmin);
 | 
						|
					allNewGrps[curTblIdx].Insert(grpmin,taddgroup);
 | 
						|
					nxtid = ((AddGroup)(allNewGrps[curTblIdx])[grpmin]).grp_id;
 | 
						|
					nxtoff = ((AddGroup)(allNewGrps[curTblIdx])[grpmin]).grp_offset;
 | 
						|
				}
 | 
						|
			}
 | 
						|
			else
 | 
						|
			{
 | 
						|
				if (romin != -1)
 | 
						|
				{
 | 
						|
					AddRO taddro = (AddRO)(allNewRos[curTblIdx][romin]);
 | 
						|
					taddro.ro_stat = 3;
 | 
						|
					allNewRos[curTblIdx].RemoveAt(romin);
 | 
						|
					allNewRos[curTblIdx].Insert(romin,taddro);
 | 
						|
					nxtid = ((AddRO)(allNewRos[curTblIdx])[romin]).ro_id;
 | 
						|
					nxtoff = (uint)((AddRO)(allNewRos[curTblIdx])[romin]).ro_offset;
 | 
						|
				}
 | 
						|
				else
 | 
						|
				{
 | 
						|
					nxtid = 0;
 | 
						|
					nxtoff = 0;
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public void processIdRecords(BinaryWriter NewFstFile,uint end)
 | 
						|
		{
 | 
						|
			int extra = 0;
 | 
						|
			uint nxtid =0, nxtoff=0;
 | 
						|
			nextIDandOffset(ref nxtid,ref nxtoff);
 | 
						|
			while (brROFst.BaseStream.Seek(0,System.IO.SeekOrigin.Current) < end)
 | 
						|
			{
 | 
						|
				// Read ID
 | 
						|
				uint id = brROFst.ReadUInt32();
 | 
						|
				// Look for new entries that precede ID
 | 
						|
				while (nxtid != 0 && nxtid < id)
 | 
						|
				{
 | 
						|
					extra += 8; // sizeof(ulong 16bit) * 2
 | 
						|
					NewFstFile.Write(nxtid);
 | 
						|
					NewFstFile.Write(nxtoff);
 | 
						|
					nextIDandOffset(ref nxtid,ref nxtoff); // passed by reference
 | 
						|
				}
 | 
						|
				// Write ID
 | 
						|
				NewFstFile.Write(id);
 | 
						|
				// Read Offset
 | 
						|
				uint off = brROFst.ReadUInt32();
 | 
						|
				// Write new offset
 | 
						|
				NewFstFile.Write(newLocation(off));
 | 
						|
			}
 | 
						|
			// Save new RO entries and Group entries
 | 
						|
			while (nxtid != 0)
 | 
						|
			{
 | 
						|
				extra += 8; // sizeof(ulong 16bit)*2
 | 
						|
				NewFstFile.Write(nxtid);
 | 
						|
				NewFstFile.Write(nxtoff);
 | 
						|
				nextIDandOffset(ref nxtid,ref nxtoff); // passed by reference
 | 
						|
			}
 | 
						|
			if (extra != 0)
 | 
						|
				AddLocation(end-1,extra);
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		/*
 | 
						|
		 * Merge the changes into the RO.FST file (usually Approved directory)
 | 
						|
		 */
 | 
						|
		public void CreateMergedFSTFile(string NewFStName)
 | 
						|
		{
 | 
						|
			BinaryWriter NewFSTFile=null;
 | 
						|
 | 
						|
			// Open a new FST file for writing
 | 
						|
			try
 | 
						|
			{
 | 
						|
				NewFSTFile = new BinaryWriter(File.Open(NewFStName,System.IO.FileMode.Create,System.IO.FileAccess.ReadWrite,FileShare.None));
 | 
						|
			}
 | 
						|
			catch (Exception e)
 | 
						|
			{
 | 
						|
				MessageBox.Show("Error Opening "+NewFStName +"\n\n" + e.Message,"Approval Error");
 | 
						|
			}
 | 
						|
			
 | 
						|
			// Write the RO.FST header
 | 
						|
			Header.Write(NewFSTFile);
 | 
						|
 | 
						|
			// Position the old FST file past the header
 | 
						|
			brROFst.BaseStream.Seek(Header.GetStructSize(),System.IO.SeekOrigin.Begin);
 | 
						|
 | 
						|
			// Loop through each database
 | 
						|
			for (short i=0; i < numDatabases; i++)
 | 
						|
			{
 | 
						|
				// Set the current table index used to access the allNewRos,
 | 
						|
				// allNewGrps, and allDifferences arrays
 | 
						|
				curTblIdx = i;
 | 
						|
 | 
						|
				// Loop through the Group and RO records
 | 
						|
				// Update the RO Group information
 | 
						|
				processGroupRecords(NewFSTFile,((ROFST_DbInfo)DatabasesInfo[i]).dbiIL);
 | 
						|
				if (((ROFST_DbInfo)DatabasesInfo[i]).dbiAW == 0)
 | 
						|
					((ROFST_DbInfo)DatabasesInfo[i]).dbiAW = maxaw;
 | 
						|
 | 
						|
				if (((ROFST_DbInfo)DatabasesInfo[i]).dbiType == 0)
 | 
						|
					((ROFST_DbInfo)DatabasesInfo[i]).dbiType = maxtype;
 | 
						|
 | 
						|
				((ROFST_DbInfo)DatabasesInfo[i]).dbiGL = whereisgl;
 | 
						|
				((ROFST_DbInfo)DatabasesInfo[i]).dbiIL = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current);
 | 
						|
				
 | 
						|
				// Loop through the ID list
 | 
						|
				processIdRecords(NewFSTFile,((ROFST_DbInfo)DatabasesInfo[i]).dbiAL);
 | 
						|
				((ROFST_DbInfo)DatabasesInfo[i]).dbiAL = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current);
 | 
						|
				// Loop through the accid list
 | 
						|
				processAccIdRecords(NewFSTFile,((ROFST_DbInfo)DatabasesInfo[i]).dbiEND,(short)((ROFST_DbInfo)DatabasesInfo[i]).dbiAW);
 | 
						|
				((ROFST_DbInfo)DatabasesInfo[i]).dbiEND = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current);
 | 
						|
			}
 | 
						|
			// Save the Database info
 | 
						|
			uint lngbuf = 0;
 | 
						|
			// Save the current location in the new fst file
 | 
						|
			uint dblength = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current);
 | 
						|
			NewFSTFile.Write(lngbuf);
 | 
						|
			NewFSTFile.Write(numDatabases);
 | 
						|
			uint lngval;
 | 
						|
			ROFST_DbInfo tmpdbinfo = new ROFST_DbInfo();
 | 
						|
			lngval = (uint)(tmpdbinfo.GetStructSize() * numDatabases);
 | 
						|
			for (int i=0;i<numDatabases;i++)
 | 
						|
			{
 | 
						|
				NewFSTFile.Write(((ROFST_DbInfo)DatabasesInfo[i]).dbiID);
 | 
						|
				NewFSTFile.Write(((ROFST_DbInfo)DatabasesInfo[i]).dbiType);
 | 
						|
				NewFSTFile.Write(((ROFST_DbInfo)DatabasesInfo[i]).dbiAW);
 | 
						|
				NewFSTFile.Write(((ROFST_DbInfo)DatabasesInfo[i]).dbiGL);
 | 
						|
				NewFSTFile.Write(((ROFST_DbInfo)DatabasesInfo[i]).dbiIL);
 | 
						|
				NewFSTFile.Write(((ROFST_DbInfo)DatabasesInfo[i]).dbiAL);
 | 
						|
				NewFSTFile.Write(((ROFST_DbInfo)DatabasesInfo[i]).dbiEND);
 | 
						|
				NewFSTFile.Write(lngval);
 | 
						|
				lngval += (uint)((ROFST_DbInfo)DatabasesInfo[i]).dbiTitle.Length + 1;
 | 
						|
				NewFSTFile.Write(lngval);
 | 
						|
				lngval += (uint)((ROFST_DbInfo)DatabasesInfo[i]).dbiAP.Length + 1;
 | 
						|
			}
 | 
						|
			for (short i=0;i<numDatabases;i++)
 | 
						|
			{
 | 
						|
				WriteString(NewFSTFile,((ROFST_DbInfo)DatabasesInfo[i]).dbiTitle,true);
 | 
						|
				WriteString(NewFSTFile,((ROFST_DbInfo)DatabasesInfo[i]).dbiAP,true);
 | 
						|
			}
 | 
						|
			// locate the end
 | 
						|
			uint dbend = (uint)NewFSTFile.Seek(0,System.IO.SeekOrigin.Current); // ftell(ofile)
 | 
						|
			// How long is the db info
 | 
						|
			NewFSTFile.Seek((int)dblength,System.IO.SeekOrigin.Begin);
 | 
						|
			lngbuf = dbend-dblength-4; //dbend-dblength-sizeof(dblength)
 | 
						|
			NewFSTFile.Write(lngbuf);
 | 
						|
			// Go to the beginning of the new file
 | 
						|
			NewFSTFile.Seek(0,System.IO.SeekOrigin.Begin);
 | 
						|
			// Save the header again
 | 
						|
			if (Header.hcYear==0)
 | 
						|
				Header.SetHeader(dblength); // sets the header and date/time
 | 
						|
			else
 | 
						|
				Header.dboffset = dblength;
 | 
						|
			Header.Write(NewFSTFile);
 | 
						|
			NewFSTFile.Flush();
 | 
						|
			NewFSTFile.Close();
 | 
						|
			uint test = (uint) Header.hcHund;
 | 
						|
			// stamp the new FST file with the RO.FST header date/time
 | 
						|
			DateTime dt = new DateTime((int)Header.hcYear,(int)Header.hMonth,(int)Header.hDay,(int)Header.hcHour,(int)Header.hcMin,(int)Header.hcSec,(int)Header.hcHund);
 | 
						|
			File.SetLastWriteTime(NewFStName,dt);
 | 
						|
		}
 | 
						|
	}
 | 
						|
/*************************************************************************/
 | 
						|
 | 
						|
	public class strEntry
 | 
						|
	{
 | 
						|
 | 
						|
		public strEntry()
 | 
						|
		{
 | 
						|
		}
 | 
						|
 | 
						|
		public virtual string toText(int mi){return "";}
 | 
						|
 | 
						|
		public virtual int getLength(int mi){return 0;}
 | 
						|
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	
 | 
						|
	public class seText : strEntry
 | 
						|
	{
 | 
						|
		public string str;
 | 
						|
		public int len;
 | 
						|
 | 
						|
		public seText(string instr, int inlen)
 | 
						|
		{
 | 
						|
			str = instr.Substring(0,inlen);
 | 
						|
			len = inlen;
 | 
						|
		}
 | 
						|
 | 
						|
		public override string toText(int mi)
 | 
						|
		{
 | 
						|
			return str;
 | 
						|
		}
 | 
						|
 | 
						|
		public override int getLength(int mi)
 | 
						|
		{
 | 
						|
			return len;
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	public class seUser : strEntry
 | 
						|
	{
 | 
						|
		string uvalue;
 | 
						|
		int len;
 | 
						|
 | 
						|
		public seUser(string str, int l)
 | 
						|
		{
 | 
						|
			uvalue = ROProcessTools.evaluate(str,l);
 | 
						|
			len = uvalue.Length;
 | 
						|
		}
 | 
						|
 | 
						|
		public override string toText(int mi)
 | 
						|
		{
 | 
						|
			return uvalue;
 | 
						|
		}
 | 
						|
 | 
						|
		public override int getLength(int mi)
 | 
						|
		{
 | 
						|
			return len;
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	public class strList
 | 
						|
	{
 | 
						|
		public varList vList;
 | 
						|
		public menuList mList;
 | 
						|
		private ArrayList aryStrEntry;
 | 
						|
 | 
						|
		public strList(string str)
 | 
						|
		{
 | 
						|
			vList = new varList();
 | 
						|
			mList = new menuList();
 | 
						|
			aryStrEntry = new ArrayList();
 | 
						|
			Process(str,str.Length);
 | 
						|
		}
 | 
						|
 | 
						|
		public strList(string str, int l, varList vl, menuList ml)
 | 
						|
		{
 | 
						|
			if (vl == null)
 | 
						|
				vList =  new varList();
 | 
						|
			else
 | 
						|
				vList = vl;
 | 
						|
			if (ml == null)
 | 
						|
				mList = new menuList();
 | 
						|
			else
 | 
						|
				mList = ml;
 | 
						|
			if (aryStrEntry == null)
 | 
						|
				aryStrEntry = new ArrayList();
 | 
						|
			Process(str.Substring(0,l),l);
 | 
						|
		}
 | 
						|
 | 
						|
		public void Add(strEntry se)
 | 
						|
		{
 | 
						|
			aryStrEntry.Add(se);
 | 
						|
		}
 | 
						|
 | 
						|
		public void processCondition(string cnd, string opt, int lc, int lo)
 | 
						|
		{
 | 
						|
			// equaluate condition
 | 
						|
			string stat = ROProcessTools.evaluate(cnd,lc);
 | 
						|
			int ls = stat.Length;
 | 
						|
			// look for match - remember default
 | 
						|
			string match=null;
 | 
						|
			int matchlen = 0;
 | 
						|
			string def = null;
 | 
						|
			int deflen = 0;
 | 
						|
			while (lo > 0 && match == null)
 | 
						|
			{
 | 
						|
				int end = ROProcessTools.matchingBrace(opt);
 | 
						|
				int eq = opt.IndexOf('=');
 | 
						|
				int len = end + 1; // +1 to include the '}'
 | 
						|
				int li = eq-1;
 | 
						|
				int ld = len-li-3; // One for '{', '=' and '}'
 | 
						|
				if (def == null || eq == 1)
 | 
						|
				{
 | 
						|
					def = opt.Substring(eq+1,ld);
 | 
						|
					deflen =  ld;
 | 
						|
				}
 | 
						|
				if (ls == li && stat.StartsWith(opt.Substring(1,li)))
 | 
						|
					{
 | 
						|
					match = opt.Substring(eq+1,ld);
 | 
						|
					matchlen = ld;
 | 
						|
				}
 | 
						|
				opt =  opt.Substring(len);
 | 
						|
				lo -= len;
 | 
						|
			}
 | 
						|
			// if match process option - or process default
 | 
						|
			if (match == null)
 | 
						|
			{
 | 
						|
				match = def;
 | 
						|
				matchlen = deflen;
 | 
						|
			}
 | 
						|
			Process(match,matchlen);
 | 
						|
		}
 | 
						|
 | 
						|
		public void processBrace(string str, int l, ref int nfnd)
 | 
						|
		{
 | 
						|
			int nxt = ROProcessTools.nextDelimiter("{=",str,l); // -1 means not found
 | 
						|
			if(nxt == -1) // varUse
 | 
						|
			{
 | 
						|
				strList found = null;
 | 
						|
				found = vList.lookFor(str,l);
 | 
						|
				if (found != null)
 | 
						|
					Add(new seVarUse(found));
 | 
						|
				else
 | 
						|
					nfnd = 1;
 | 
						|
			}
 | 
						|
			else
 | 
						|
			{
 | 
						|
				if (str[nxt] == '{') // conditonal or menu
 | 
						|
				{
 | 
						|
					if(nxt==0)
 | 
						|
					{ // menu
 | 
						|
						mList.Process(str,l,vList);
 | 
						|
						Add(new seMenuUse(mList));
 | 
						|
					} 
 | 
						|
					else 
 | 
						|
					{ // conditional
 | 
						|
						processCondition(str, str.Substring(nxt), nxt, l -nxt);
 | 
						|
					}
 | 
						|
				}
 | 
						|
				else 
 | 
						|
				{ // must be variable definiton
 | 
						|
					vList.Add(str, str.Substring(nxt+1), nxt, l - nxt - 1, mList);
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
		public void Process (string str, int len)
 | 
						|
		{
 | 
						|
			int nxtDlm = -1; // -1 = not found
 | 
						|
			while (len > 0)
 | 
						|
			{
 | 
						|
				nxtDlm = ROProcessTools.nextDelimiter("{",str,len);
 | 
						|
				if (nxtDlm == -1)
 | 
						|
				{
 | 
						|
					// add entire string as is
 | 
						|
					Add(new seText(str,len));
 | 
						|
					//str = str.Substring(len);  don't think we need to do this
 | 
						|
					len = 0;
 | 
						|
				}
 | 
						|
				else
 | 
						|
				{
 | 
						|
					int cnt = 0;
 | 
						|
					if (nxtDlm > 0)
 | 
						|
					{
 | 
						|
						// add preceeding text
 | 
						|
						Add(new seText(str,nxtDlm));
 | 
						|
						str = str.Substring(nxtDlm);
 | 
						|
						len-=nxtDlm;
 | 
						|
					}
 | 
						|
					// add text group by delimiter, including
 | 
						|
					// the delimiters
 | 
						|
					nxtDlm = ROProcessTools.matchingBrace(str)+1;
 | 
						|
					cnt = nxtDlm;
 | 
						|
					int nfnd = 0;
 | 
						|
					processBrace(str.Substring(1),cnt-2,ref nfnd);
 | 
						|
					if (nfnd > 0)
 | 
						|
					{
 | 
						|
						Add(new seText(str,cnt));
 | 
						|
					}
 | 
						|
					// position to next delimiter grouping
 | 
						|
					len -= cnt;
 | 
						|
					str = str.Substring(nxtDlm);
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
		public string toText(int mi)
 | 
						|
		{
 | 
						|
			StringBuilder bldstr = new StringBuilder();
 | 
						|
			for (int i=0; i < aryStrEntry.Count; i++)
 | 
						|
			{
 | 
						|
				bldstr.Append(((strEntry)aryStrEntry[i]).toText(mi));
 | 
						|
			}
 | 
						|
			return bldstr.ToString();
 | 
						|
		}
 | 
						|
 | 
						|
		public int getLength(int mi)
 | 
						|
		{
 | 
						|
			int rtnval = 0;
 | 
						|
			for (int i=0; i < aryStrEntry.Count; i++)
 | 
						|
			{
 | 
						|
				rtnval += (((strEntry)aryStrEntry[i]).getLength(mi));
 | 
						|
			}
 | 
						|
			return rtnval;
 | 
						|
		}
 | 
						|
 | 
						|
		public int menuCount()
 | 
						|
		{
 | 
						|
			return mList.getCount();
 | 
						|
		}
 | 
						|
 | 
						|
		public string getIds(ref int cnt)
 | 
						|
		{
 | 
						|
			// return a string of the IDs
 | 
						|
			return mList.getIds(ref cnt);
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
 | 
						|
	public class strList2
 | 
						|
	{
 | 
						|
 | 
						|
		private ArrayList aryStrEntry;
 | 
						|
 | 
						|
		public strList2(string str)
 | 
						|
		{
 | 
						|
			int l=str.Length;
 | 
						|
			if (aryStrEntry == null)
 | 
						|
				aryStrEntry = new ArrayList();
 | 
						|
			while(l > 0)
 | 
						|
			{
 | 
						|
				int ptr=ROProcessTools.nextDelimiter("<",str,l);
 | 
						|
				int cptr = (ptr==-1)?-1:ROProcessTools.nextDelimiter(">",str.Substring(ptr,str.Length - ptr),str.Length-ptr);
 | 
						|
				if(ptr == -1 || (ptr>-1 && cptr == -1))
 | 
						|
				{
 | 
						|
					Add(new seText(str,l));
 | 
						|
					l=0;
 | 
						|
				} 
 | 
						|
				else 
 | 
						|
				{
 | 
						|
					int cnt = ptr; //(int)(ptr-str);
 | 
						|
					if(cnt > 0)
 | 
						|
					{
 | 
						|
						Add(new seText(str,cnt));
 | 
						|
						l-=cnt;
 | 
						|
						str = str.Substring(ptr); // str=ptr
 | 
						|
					}
 | 
						|
					ptr=ROProcessTools.nextDelimiter(">",str,l)+1;
 | 
						|
					cnt = ptr;//(int)(ptr-str);
 | 
						|
					string tmpstr = str.Substring(1);
 | 
						|
					Add(new seUser(tmpstr,cnt-2));
 | 
						|
					l-=cnt;
 | 
						|
					str = str.Substring(ptr);//str=ptr;
 | 
						|
				}
 | 
						|
			}
 | 
						|
		}
 | 
						|
 | 
						|
		public void Add (strEntry se)
 | 
						|
		{
 | 
						|
			aryStrEntry.Add(se);
 | 
						|
		}
 | 
						|
 | 
						|
		public string toText()
 | 
						|
		{
 | 
						|
			StringBuilder bldstr = new StringBuilder();
 | 
						|
			for (int i=0; i < aryStrEntry.Count; i++)
 | 
						|
			{
 | 
						|
				bldstr.Append(((strEntry)aryStrEntry[i]).toText(0));
 | 
						|
			}
 | 
						|
			return bldstr.ToString();
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	public class varEntry
 | 
						|
	{
 | 
						|
		string Name;
 | 
						|
		int Len;
 | 
						|
		strList Definition;
 | 
						|
 | 
						|
		public varEntry(string InName, string InDef, int lenInName, int lenInDef, varList vlist, menuList mlist)
 | 
						|
		{
 | 
						|
			Definition =  new strList(InDef,lenInDef,vlist,mlist);
 | 
						|
			Name = InName.Substring(0,lenInName);
 | 
						|
			Len = lenInName;
 | 
						|
		}
 | 
						|
 | 
						|
		public  strList lookFor(string nam, int l)
 | 
						|
		{
 | 
						|
			string tname = nam.Substring(0,l);
 | 
						|
			if (l == Len && (Name.CompareTo(tname)==0))
 | 
						|
				return Definition; // found
 | 
						|
			return null; // not found
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	public class varList
 | 
						|
	{
 | 
						|
		ArrayList varEntryAry;
 | 
						|
 | 
						|
		public varList()
 | 
						|
		{
 | 
						|
			varEntryAry = new ArrayList();
 | 
						|
		}
 | 
						|
 | 
						|
		public void Add(string InName, string InDef, int lenInName, int lenInDef, menuList mlist)
 | 
						|
		{
 | 
						|
			varEntry tmpEntry = new varEntry(InName,InDef,lenInName,lenInDef,null,mlist);
 | 
						|
			varEntryAry.Add(tmpEntry);
 | 
						|
		}
 | 
						|
 | 
						|
		public strList lookFor(string str, int len)
 | 
						|
		{
 | 
						|
			strList rtnval = null;
 | 
						|
			for (int i = 0; (rtnval == null) && (i < varEntryAry.Count); i++)
 | 
						|
			{
 | 
						|
				rtnval = ((varEntry)varEntryAry[i]).lookFor(str,len);
 | 
						|
			}
 | 
						|
			return rtnval;
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	public class seVarUse : strEntry
 | 
						|
	{
 | 
						|
		strList Def; 
 | 
						|
 | 
						|
		public seVarUse(strList d)
 | 
						|
		{
 | 
						|
			Def = d;
 | 
						|
		}
 | 
						|
 | 
						|
 | 
						|
		public override string toText(int mi)
 | 
						|
		{
 | 
						|
			return Def.toText(mi);
 | 
						|
		}
 | 
						|
 | 
						|
		public override int getLength(int mi)
 | 
						|
		{
 | 
						|
			return Def.getLength(mi);
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	public class menuEntry
 | 
						|
	{
 | 
						|
		byte id;
 | 
						|
		strList definition;
 | 
						|
 | 
						|
		public menuEntry(string idptr,string def,int li,int ld,varList vlst)
 | 
						|
		{
 | 
						|
			definition = new strList(def, ld, vlst,null);
 | 
						|
			// save the id
 | 
						|
			if(li != 0)
 | 
						|
				id=(byte)idptr[0];
 | 
						|
			else 
 | 
						|
				id=0;
 | 
						|
		}
 | 
						|
 | 
						|
		public int getLength(int mi)
 | 
						|
		{
 | 
						|
			if(mi==(int)id || mi==-1)
 | 
						|
				return definition.getLength(mi);
 | 
						|
			else
 | 
						|
				return 0;
 | 
						|
		}
 | 
						|
 | 
						|
		public virtual string toText(int mi)
 | 
						|
		{
 | 
						|
			if (mi == id || mi==-1)
 | 
						|
				return definition.toText(mi);
 | 
						|
			else
 | 
						|
				return "";
 | 
						|
		}
 | 
						|
 | 
						|
		public string getID()
 | 
						|
		{
 | 
						|
			string rtnstr = id.ToString();
 | 
						|
			return rtnstr;
 | 
						|
		}
 | 
						|
 | 
						|
		public int getCount()
 | 
						|
		{
 | 
						|
			return 1;
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
 | 
						|
	public class menuList : strEntry
 | 
						|
	{
 | 
						|
		ArrayList aryMenuList;
 | 
						|
 | 
						|
		public menuList()
 | 
						|
		{
 | 
						|
			aryMenuList = new ArrayList();
 | 
						|
		}
 | 
						|
 | 
						|
		public void Add(menuEntry MnuEntry)
 | 
						|
		{
 | 
						|
			aryMenuList.Add(MnuEntry);
 | 
						|
		}
 | 
						|
 | 
						|
		private int _getLength(int mi)
 | 
						|
		{
 | 
						|
			int lcnt = aryMenuList.Count;
 | 
						|
			int rtnval =0;
 | 
						|
 | 
						|
			for (int i=0; i < lcnt; i++)
 | 
						|
			{
 | 
						|
				rtnval += (((menuEntry)aryMenuList[i])).getLength(mi);
 | 
						|
			}
 | 
						|
			return rtnval;
 | 
						|
		}
 | 
						|
 | 
						|
		private int _getLenAndLookat(int mi, ref int lookat)
 | 
						|
		{
 | 
						|
			int len =0;
 | 
						|
			lookat = mi;
 | 
						|
 | 
						|
			if (aryMenuList.Count > 0)
 | 
						|
			{
 | 
						|
				len=_getLength(lookat);
 | 
						|
				if (len ==0)
 | 
						|
				{
 | 
						|
					lookat = 0;
 | 
						|
					len = _getLength(lookat);
 | 
						|
				}
 | 
						|
				if (len == 0)
 | 
						|
				{
 | 
						|
					lookat = -1;
 | 
						|
					len = _getLength(lookat);
 | 
						|
				}
 | 
						|
			}
 | 
						|
 | 
						|
			return len;
 | 
						|
		}
 | 
						|
 | 
						|
		public override int getLength(int mi)
 | 
						|
		{
 | 
						|
			int lookat=0;
 | 
						|
			return _getLenAndLookat(mi,ref lookat);
 | 
						|
		}
 | 
						|
 | 
						|
		public override string toText(int mi)
 | 
						|
		{
 | 
						|
			StringBuilder rtnstr = new StringBuilder();
 | 
						|
			int lookat=0;
 | 
						|
 | 
						|
			int len = _getLenAndLookat(mi,ref lookat);
 | 
						|
			if (aryMenuList.Count > 0)
 | 
						|
			{
 | 
						|
				for (int i = 0; i< aryMenuList.Count; i++)
 | 
						|
				{
 | 
						|
					string roval = ((menuEntry)aryMenuList[i]).toText(lookat);
 | 
						|
					if (lookat == -1)
 | 
						|
					{
 | 
						|
						// For Approve Individual, show all possible RO
 | 
						|
						// values (for conditional RO's)
 | 
						|
						// We may need to add a flag here later on when
 | 
						|
						// this logic is used in the Procedure Editor.
 | 
						|
						if (i > 0 && !roval.Equals(""))
 | 
						|
							rtnstr.Append("\n");
 | 
						|
					}
 | 
						|
					rtnstr.Append(roval);
 | 
						|
				}
 | 
						|
			}
 | 
						|
			return rtnstr.ToString();
 | 
						|
		}
 | 
						|
 | 
						|
		public string getIds(ref int cnt)
 | 
						|
		{
 | 
						|
			StringBuilder rtnstr = new StringBuilder();
 | 
						|
			cnt = getCount();
 | 
						|
			int arycnt = aryMenuList.Count;
 | 
						|
 | 
						|
			for (int i=0; i<arycnt; i++)
 | 
						|
			{
 | 
						|
				rtnstr.Append(((menuEntry)aryMenuList[i]).getID());
 | 
						|
			}
 | 
						|
			return rtnstr.ToString();
 | 
						|
		}
 | 
						|
 | 
						|
		public int getCount()
 | 
						|
		{
 | 
						|
			int rtncnt=0;
 | 
						|
			int arycnt = aryMenuList.Count;
 | 
						|
			for (int i=0; i<arycnt; i++)
 | 
						|
			{
 | 
						|
				rtncnt+=(((menuEntry)aryMenuList[i]).getCount());
 | 
						|
			}
 | 
						|
			return rtncnt;
 | 
						|
		}
 | 
						|
 | 
						|
		public void Process(string str,int l, varList v)
 | 
						|
		{
 | 
						|
			// get each piece and add a new entry
 | 
						|
			do 
 | 
						|
			{
 | 
						|
				int end= ROProcessTools.matchingBrace(str);
 | 
						|
				int eq=str.IndexOf('=');
 | 
						|
				int len = end + 1;	// +1 to include the '}'
 | 
						|
				int li = eq - 1;
 | 
						|
				int ld = len-li-3;	// One for '{', '=' and '}'
 | 
						|
				Add(new menuEntry(str.Substring(1),str.Substring(eq+1),li,ld,v));
 | 
						|
				// point to the next piece
 | 
						|
				str = str.Substring(len);
 | 
						|
				l -= len;
 | 
						|
			} while(l > 0);
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
	public class seMenuUse : strEntry
 | 
						|
	{
 | 
						|
		menuList ml;
 | 
						|
 | 
						|
		public seMenuUse(menuList m)
 | 
						|
		{
 | 
						|
			ml=m;
 | 
						|
		}
 | 
						|
 | 
						|
		public override string toText(int mi)
 | 
						|
		{
 | 
						|
			return ml.toText(mi);
 | 
						|
		}
 | 
						|
 | 
						|
		public override int getLength(int mi)
 | 
						|
		{
 | 
						|
			return ml.getLength(mi);
 | 
						|
		}
 | 
						|
	}
 | 
						|
 | 
						|
}
 |