The <vat.h> header file
This header file contains the following functions:
AddSymToFolder DerefSym EM_moveSymFromExtMem
EM_moveSymToExtMem EM_twinSymFromExtMem FindSymInFolder
FolderAdd FolderAddTemp FolderClear
FolderCount FolderCur FolderCurTemp
FolderDel FolderDelAllTemp FolderDelTemp
FolderFind FolderGetCur FolderOp
FolderRename HSymDel HSYMtoName
IsMainFolderStr MakeHSym SymAdd
SymAddMain SymAddTwin SymCmp
SymCpy SymCpy0 SymDel
SymDelTwin SymFind SymFindFirst
SymFindFolderName SymFindHome SymFindMain
SymFindNext SymFindPrev SymFindPtr
SymMove TempFolderName
the following macro constructors:
$
and the following constants and predefined types:
Bool CompatFlags FolderOpFlags
FolderStats HANDLE H_NULL
HSym HS_NULL NULL
SYM_ENTRY SymFlags
Functions
HSym SymFind (const char *SymName);
Finds a symbol.
SymFind searches the variables allocation table (VAT) for a symbol (i.e. variable)
SymName. SymName may also contain a folder name together with
the symbol name (separated by "\"), else only currently active
folder will be searched. SymFind returns a structure of type HSym,
which contains the handle of the variable table list which belongs to the folder
(current, or folder given in the name), and the offset from the beginning ot the list to the actual VAT symbol
entry. Use DerefSym to get a pointer to the actual VAT
symbol entry instead. In a case of error (for example, if the symbol does not exist), SymFind
returns HS_NULL. Note that most reserved symbols (i.e. system variables)
are not stored in the VAT table, so you can not locate them using SymFind.
NOTE: SymName is not an ordinary C string. Instead, this is a sequence
of characters which starts with zero character ('\0') and terminates with zero
character too, and all TIOS routines for VAT handling needs a pointer to the
TERMINATING zero byte as an input argument, which is a bit twisty. So, to search for a symbol named
"tetris", instead of
hsym = SymFind ("tetris");
you must do the following:
hsym = SymFind ("\0tetris"+7);
To make this job easier, a constructor macro $ is implemented,
so you may simply do
hsym = SymFind ($(tetris));
Note also that all legal TIOS symbol names must be in lowercase!
HSym SymFindMain (const char *SymName);
Finds a symbol in the main folder.
SymFindMain acts like SymFind, but searches only the main
folder, regardless of the current active folder, even if SymName contains
the folder name together with the symbol name. See SymFind
for more info. It is useful for searching some symbols such as the system
reserved equations ('Y1'...'Y99', 'RegEq' etc.) which are always stored in the
"main" folder and cannot be moved to a different folder.
HSym SymFindHome (const char *SymName);
Finds a folder.
SymFindHome searches the folder table part of variables allocation table (VAT) for a
folder named SymName (in fact, it searches through a pseudo-folder called
"home", which contains all other folders).
SymFindHome returns a structure of type HSym,
which contains the handle of the folder table list of the VAT, and the offset from the
beginning ot the list to the actual VAT symbol entry. Use DerefSym
to get a pointer to the actual VAT symbol entry instead. In a case of error (for example, if
the folder does not exist), SymFindHome returns HS_NULL. See also notes related to
SymFind for more info about SymName.
NOTE: I don't know what DoorsOS does to find the handle of the folder list, but as far
as I know, the only legal method is the following:
FolderListHandle = SymFindHome("\0main"+5).folder;
HSym FindSymInFolder (const char *SymName, const char *FolderName);
Finds a symbol in a given folder.
FindSymInFolder acts like SymFind, but searches for a symbol
in the folder given by FolderName. See SymFind
for more info and rules about SymName and FolderName. As far
as I know, the statement
hsym = FindSymInFolder ($(tetris), $(games));
acts exactly the same as the statement
hsym = SymFind ($(games\\tetris));
See SymFind for info about $ constructor.
Dereferences a symbol.
DerefSym dereferences the symbol by converting Sym (which is return value from many
TIOS VAT functions) into the actual VAT entry. DerefSym returns a pointer to the entry,
which is a pointer to the structure
of type SYM_ENTRY, which represents a VAT entry. Returns
NULL in a case of error. Beware that VAT entries may moved during the heap compression,
so SYM_ENTRY pointers may become invalid after the heap compession.
DerefSym may be simulated using HeapDeref.
For example, the statement
SymPtr = DerefSym (hsym);
is equal to the statement
SymPtr = (SYM_ENTRY*)((char*)HeapDeref(hsym.folder) + hsym.offset);
NOTE: I don't know what DoorsOS does to find the handle of the main folder, but one method
which is certainly legal is the following:
MainHandle = DerefSym(SymFindHome("\0main"+5))->handle;
SYM_ENTRY *SymFindPtr (const char *SymName, unsigned short Flags);
Finds a symbol and returns a pointer to the VAT entry.
SymFindPtr acts like SymFind etc. but instead of HSym
structure, it returns a pointer to the actual VAT entry. Returns NULL in a case of error.
So, it acts somewhat as a combination of SymFind etc.
and DerefSym.
Flags is an additional argument which determines the searching method. It is a
set of binary flags. The exact meaning of these flags are still unknown for me, but at
the moment, I surely know the following:
- When Flags = 0, the searching is performed like using
SymFind function (i.e. through current or given folder);
- When Flags = 4, the searching is performed like using
SymFindMain function (i.e. through main folder only).
What I also know is that when b15 in Flags is set, a searching is somewhat related to
the folder list, and it is possible to search for folders too. But, I still can't conclude
EXACT meaning of these flags. So, instead of giving uncertain information, I will stop here.
Everything about this function presented so far is certainly true. Fortunately, TIOS set of VAT functions is reach
enough that eventual additional possibilities of this function may be simulated using other
known functions. Any additional info will be welcomed, if someone knows more than me.
As an example of usage, this is a legal method how to lock a variable named "tetris":
SymFindPtr($(tetris), 0)->flags.bits.locked = 1;
See SymFind for info about $ constructor.
Checks whether a folder exists.
FolderFind searches for a folder SymName through the folder table in the VAT,
and returns the following result:
- MAIN_FOLDER, if SymName is the "main" folder;
- FOLDER_TABLE, if a folder with name SymName exists;
- NOT_FOUND, if a folder with name SymName does not exists;
- BAD_FOLDER, if a symbol with name SymName is really present in the folder table,
but does not represents a folder (i.e. folder bit is not set); this return value
probably represents an invalid entry.
These constants are defined in enum FolderStats.
See SYM_ENTRY for more info about structure of VAT entry, and
SymFind for rules about SymName.
HSym SymAdd (const char *SymName);
Adds a symbol.
SymAdd creates a new entry in the variables allocation table (VAT) for a symbol
SymName, and returns a result like in SymFind
function. If the symbol SymName already exists, SymAdd deletes the old
symbol before creating a new one (except if SymName is a folder name;
such case is considered as an error). In a case of error, SymAdd returns HS_NULL.
This function may throw out an error if the symbol already exist and it is locked.
See SymFind and DerefSym for more info.
SymName may also contain a folder name together with the symbol name
(separated by "\"). In a such case, the symbol will be added in the given folder.
If the given folder does not exist, a dialog will appear which asks the user whether
a new folder will be created. If the answer is "NO", a "Folder" error will be thrown
(beware that opening a dialog may change a system font, so usage of
SaveScrState and RestoreScrState
is highly recommended in all cases when you expect that a folder creationdialog might appear).
If SymName does not contain a folder name, the symbol entry will be created
in the current active folder. This routine does not check for reserved symbol names and
so caution must be used when using this routine.
Note that SymAdd adds only an entry in the VAT with an empty handle; it does not allocate
any space for the actual variable. To actually create a variable named "example", do
the following (assuming that there was no errors in intermediate steps):
SymPtr = DerefSym (SymAdd ($(example)));
VarPtr = (char*)HeapDeref (SymPtr->handle = HeapAlloc(100));
Now, 100 bytes of space for the variable (together with the valid handle in the VAT entry) is
created, and VarPtr points to it (see HeapAlloc and
HeapDeref for more info). It does not mean that the actual
length of the variable must be 100 bytes: it is only an allocated amount of the memory.
To create a concrete
variable, you must fill the space pointed to by VarPtr with a valid data which depends of
the wanted type of the variable. The format of some variable types (STR, PIC, TEXT etc.) may
be found on doors.ticalc.org. For example, to create
one-character long string variable with content "A", do the following:
VarPtr[0] = 0; // 2 bytes: length of the variable - 2
VarPtr[1] = 4;
VarPtr[2] = 0; // zero marks a begining of the actual variable data
VarPtr[3] = 'A'; // actual data
VarPtr[4] = 0; // end-of-string marker
VarPtr[5] = STR_TAG; // the last byte is a type (see STR_TAG)
NOTE: It is very dangerous to add a new entry in the VAT without allocating a memory
space, and without assigning the handle in the entry. I didn't check whether a real
TI-89 crashes after this, but the debugger in the VTI chrashes!? Rusty, this is a bug...
HSym SymAddMain (const char *SymName);
Adds a symbol in the main folder.
SymAddMain acts like SymAdd, but adds the VAT entry in the main
folder list, regardless of the current active folder, even if SymName contains
the folder name together with the symbol name. See SymAdd
for more info.
HSym AddSymToFolder (const char *SymName, const char *FolderName);
Adds a symbol in a given folder.
AddSymToFolder acts like SymAdd, but adds the VAT entry
in the folder given by FolderName. See SymAdd and
SymFind
for more info and rules about SymName and FolderName.
NOTE: This routine is a bit buggy: if the folder FolderName does not
exist, a behaviour of this routine is very uncertain, and may result with a crash.
HANDLE FolderAdd (const char *SymName);
Creates a folder.
FolderAdd creates a new folder with name SymName. See
SymFind for rules about SymName. FolderAdd returns
a handle to the created folder (more precise, to the VAT variable list which belongs to
the created folder). Returns H_NULL in a case of error (for example, the folder
already exists, or there is not enough memory). Note that reserved names are not valid folder names
and that this routine does not check for reserved names. It is up to the caller to validate
the folder name before calling this routine. This routine may cause heap compression.
This routine also can be used to create temporary folders
(see also FolderAddTemp) whose names begin with a number and are not
displayed in VAR-LINK dialog. Temporary folder numbers '0001'...'8192' are reserved for
keeping TI-BASIC local symbols, folder number '9998' is used in Data/Matrix Editor,
and folder number '9999' is reserved for various temporary storage.
HSym SymAddTwin (const char *SymName);
Creates a twin symbol.
SymAddTwin creates a twin entry in the variables allocation table (VAT) for an
existing symbol SymName. Twin symbol is, in fact, another entry in the VAT
with the same variable name, but with different handle. TIOS creates twin symbols
during execution of archived programs, just before the normal symbol in the VAT table
(see EM_twinSymFromExtMem).
A twin symbol is "stronger" that normal symbol, i.e. existence of a twin symbol temporary hides the symbol with the same
name, until the twin symbol is deleted. Twin symbols has "twin" bit set in the VAT
entry (see SYM_ENTRY for a structure of VAT entry), but in
VAR-LINK menu, it is shown as "archived". SymAddTwin returns the same result as
SymAdd (HS_NULL in a case of error). If the symbol SymName
does not exist, this is also an error.
short EM_moveSymToExtMem (const char *SymName, HSym Sym);
Moves a symbol from the RAM to the archive memory.
EM_moveSymToExtMem archives a symbol. The symbol may be described either by
symbol name SymName (in this case, parameter Sym should be
set to HS_NULL) or by HSym structure
Sym (in this case, SymName must be NULL).
See SymFind for rules about SymName.
EM_moveSymToExtMem returns TRUE if the operation was
successful, else returns FALSE.
short EM_moveSymFromExtMem (const char *SymName, HSym Sym);
Moves a symbol from the archive memory to the RAM.
EM_moveSymFromExtMem unarchives an archived symbol. The symbol may be described either by
symbol name SymName (in this case, parameter Sym should be
set to HS_NULL) or by HSym structure
Sym (in this case, SymName must be NULL).
See SymFind for rules about SymName.
EM_moveSymFromExtMem returns TRUE if the operation was
successful, else returns FALSE.
HSym EM_twinSymFromExtMem (const char *SymName, HSym Sym);
Creates a twin symbol, then copies a symbol from the archive memory to it.
EM_twinSymFromExtMem first calls SymAddTwin to create a twin
symbol, then copies the archived symbol to it. The symbol may be described either by
symbol name SymName (in this case, parameter Sym should be
set to HS_NULL) or by Hsym structure
Sym (in this case, SymName must be NULL).
See SymFind for rules about SymName.
TIOS uses EM_twinSymFromExtMem when it need to execute archived program.
EM_twinSymFromExtMem returns a HSym structure which represents
a newly created symbol (or HS_NULL in a case of error).
EM_twinSymFromExtMem returns Sym itself if the symbol is not archived.
Deletes a symbol.
SymDel deletes the symbol SymName and returns TRUE if the operation was successful,
else returns FALSE. See SymFind for rules
about SymName. Note that this routine will delete symbols even if they are locked or
in-use! Do not call SymDel to delete a folder, twin or archived symbols (for these purposes,
see FolderDel and SymDelTwin).
short HSymDel (HSym Sym);
Deletes a symbol pointed to by HSym.
HSymDel acts exactly like SymDel, except it takes
a structure of type HSym as an input parameter instead of the symbol name.
See also SymFind for more info.
NOTE: This routine assumes that Sym is valid; if it is not, it may throw
an error (for example, if Sym represents a reserved symbol like "main", or if the
referenced symbol is in-use). If HSymDel is called to delete a folder than that folder MUST
be empty! Also do not use HSymDel to delete twin or archived variables.
This routine modifies the VAT table, so it invalidates any other existing HSym-s.
The caller must be sure that the VAT table has not been changed since the Sym
was obtained.
Deletes a folder, including all files in it.
FolderDel deletes the folder SymName
including all files in it, and returns TRUE if the operation was successful,
else returns FALSE (e.g. if the folder is not found). See SymFind for rules
about SymName. If the folder SymName is the current folder, the new current
folder after deleting will become the "main" folder.
If the folder SymName is "main", then all symbols from it will be deleted,
but the folder itself will remain intact. Beware that this routine will delete all symbols in
the folder even if they are locked, in use, or archived!
NOTE: This function was buggy in TIGCCLIB releases prior to 2.3. I didn't know that the original
TIOS entry called "FolderDel" requires in fact two parameters: another one is a Boolean flag. As
this parameter was not passed before, the behaviour of this routine was random (see also
FolderClear). Now, to keep the compatibility with already written
programs, I modified FolderDel to always pass FALSE as an extra parameter
(in this case, FolderDel behaves as described above; when it is TRUE,
FolderDel behaves as FolderClear).
Deletes all files in the folder.
FolderClear deletes all files in the folder SymName, but does not remove the folder
itself. Returns TRUE if the operation was successful,
else returns FALSE (e.g. if the folder is not found). See SymFind for rules
about SymName. Beware that this routine will delete all symbols in
the folder even if they are locked, in use, or archived!
NOTE: This function calls original TIOS entry called "FolderDel", but passes an
extra Boolean parameter set to TRUE. See also note given with
FolderDel function.
short SymDelTwin (SYM_ENTRY *SymPtr);
Deletes a twin symbol.
SymDelTwin deletes a twin symbol (see SymAddTwin for more info
about twin symbols) whose VAT entry is SymPtr. Returns TRUE if
the operation was successful, else returns FALSE.
Moves a symbol.
SymMove moves the symbol SrcName to the symbol DestName
(see SymFind for rules about SrcName and DestName).
Both SrcName and DestName may also contain a folder name together with the
symbol name (separated by "\"). If none of the names does not contain a folder name,
moving will be simply reduced to renaming. If the destination folder does not exist, a dialog
will appear which asks the user whether a new folder will be created. If the answer is "NO", a
"Folder" error will be thrown. Destination symbol will be deleted before moving, if such
symbol exists. SymMove returns TRUE if the operation was successful,
else returns FALSE.
NOTE: Check whether SrcName exists before applying this command, because the
destination symbol DestName (if exists) will be deleted even in a case of an error!
Renames a folder.
FolderRename renames the folder SrcName to the name DestName.
Returns TRUE if the operation was successful
(SrcName must exist and must be a folder, and DestName
must not exist),
else returns FALSE. See SymFind for rules
about folder names. Note that this routine does not check for reserved names,
and may throw an error if renaming to or from a reserved name (e.g. "main"),
or if any variable in the given folder is in-use.
short HSYMtoName (HSym Sym, char *buffer);
Determines a full path of a symbol.
HSYMtoName fills buffer with a full-path name (i.e. "folder\name")
of the symbol given by HSym structure Sym. See
SymFind for more info about HSym names. The buffer must be
at least 18 bytes long, and it will be filled with a standard C zero-terminated string.
HSYMtoName returns TRUE if the operation was successful,
else returns FALSE.
Sets the current active folder.
FolderCur sets the current active folder to SymName (see SymFind
for rules about SymName). Returns TRUE if the operation was successful,
else returns FALSE (e.g. if the folder name is invalid).
nonSys is a flag which normally need to be
FALSE. When it is set to TRUE, FolderCur calls
SymFindNext repeatedly until the first non-system variable in
this folder is reached (I thought this before; however, TI says that it should be always
TRUE, else the current graph may become invalid, so maybe it is better
to do what they says about it).
NOTE: The folder name in the status line will not be changed automatically using this command.
You must change it manually using function ST_folder.
Determines the current active folder.
FolderGetCur fills buffer with a name of the current active folder.
The buffer must be at least 9 bytes long, and it will be filled with a standard C
zero-terminated string.
unsigned short FolderCount (const SYM_ENTRY *SymPtr);
Determines a number of symbols in a folder.
FolderCount returns a number of symbols in the folder which VAT entry is
SymPtr. For example, to determine a number of symbols in the main
folder, do the following:
number = FolderCount (DerefSym (SymFindHome($(main))));
See SymFind, SymFindHome and
DerefSym for more info.
Creates a temporary folder name.
TempFolderName converts the number TempNum in a four-digit string which
corresponds to the given number (i.e. 12 will be converted into "0012"). This
string will begin with '\0' character, and TempFolderName will return a pointer
to the terminating '\0' character, as expected by many TIOS VAT routines (see
SymAdd for more info about symbol names). TIOS will accept
such "numeric" folder names, but they are invisible for the TI-Basic system,
VAR-LINK menu, etc. TIOS creates and uses such folders for storing local variables
during execution of TI-Basic programs.
Creates a temporary folder.
FolderAddTemp create the temporary folder, which name will consist of four digits
(see TempFolderName). First call of FolderAddTemp
will create a folder named "0001", the next call will create a folder named "0002",
etc. FolderAddTemp returns the name of created folder, with the same convention as
used in function TempFolderName. Created folder will be
marked as "current temporary folder" (see FolderCurTemp).
FolderAddTemp throws a "Memory" error if there is no enough space for a new folder.
Sets the current temporary folder for storing local symbols.
FolderCurTemp sets the current temporary folder for storing local symbols to SymName.
SymName must be a "numeric" symbol name as functions like
TempFolderName or FolderAddTemp
returns. FolderCurTemp returns TRUE if the operation was successful,
else returns FALSE.
Deletes a temporary folder.
FolderDelTemp deletes the last created temporary folder and selects the previous temporary
folder as current temporary folder (see FolderCurTemp). Nothing
bad will happen if the temporary folder does not exist, or in case of any eventual error.
Deletes a block of temporary folders.
FolderDelAllTemp deletes all temporary folders whose names are series of consequent
numbers starting from StartTempNum up to the first unused number, like in
following algorithm:
current = StartTempNum;
while (FolderFind (name = TempFolderName (current++)) == 3)
FolderDel (name);
The intention of this routine was very probably to delete all temporary folders when called
with StartTempNum equals to 1. But, there is a problem. This routine does not reset
the system variable which tells which is last used temporary folder number (I think that this
is a bug in TIOS). So, a next call of FolderAddTemp will not start again
from folder named "0001". This may cause various problems later. That's why I strongly recommend
avoiding this routine, and using repeated call to FolderDelTemp
instead.
SYM_ENTRY *SymFindFirst (const char *SymName, unsigned short Flags);
Searches for an entry in the VAT table.
SymFindFirst searches for a first symbol entry in the VAT table which satisfies the requirements
given by parameters Flags and SymName, and sets some internal pointers so
that SymFindNext and SymFindPrev may be
called to traverse the folder. SymName is required only for
some values of Flags (you can set it to NULL otherwise).
Flags is the collection of binary flags where bits b0, b1, b2, b3 and b4 are used (AMS 2.xx
also uses bit b5). These flags also determined how subsequent calls of
SymFindNext and SymFindPrev would
be interpreted. Many combination of bits are meaningless; here is a
complete list of meaningful values:
-
When Flags = 0 (more precise, when b0, b1 & b4 are clear), SymFindFirst
searches for a first entry in the folder table
(SymName is ignored). Subsequent calls of SymFindNext
will continue browsing only through the folder table part of VAT table (i.e. only folders
will be found).
-
When Flags = 1 (more precise, when b0 is set and b1 & b4 are clear),
SymFindFirst searches for a first symbol entry in the folder
SymName (see SymFind for more info about valid symbol names).
Subsequent calls of SymFindNext will continue browsing through the
variable table associated with this folder (i.e. only symbols in this folder will be found).
-
When Flags = 2 (more precise, when b1 is set and b0 & b4 are clear),
SymFindFirst searches for a first entry in the folder table
(SymName is ignored). Subsequent calls of SymFindNext
will continue searching through the whole VAT table, including both the folder table and
variable tables associated to each folder. More precise, after each folder, complete variable
table for this folder will be browsed before the next folder is taken in consideration.
-
When Flags = 17 (more precise, when b1 is clear and b0 & b4 are set),
SymFindFirst searches exactly for an entry of the
folder SymName through the folder table in the VAT (so, just this folder entry
will be returned if such folder exists), but later subsequent calls of
SymFindNext will continue browsing through the variable table
associated with this folder (starting from the first symbol in the folder).
-
When bit b2 in Flags is set, SymFindFirst acts as when b2 is clear (the behaviour
is determined by other bits), but temporary folders will be skipped.
See FolderAddTemp for more info about temporary folders.
This option obviously has not any sense when b0 is set.
-
When bit b3 in Flags is set, SymFindFirst acts as when b3 is clear (the behaviour
is determined by other bits), but twin entries (which are normally ignored during
traversing through the VAT table) will also be founded.
See SymAddTwin for more info about twin entries.
This option obviously has not any sense when b0 is set.
-
When bit b5 in Flags is set, SymFindFirst acts as when b5 is clear (the behaviour
is determined by other bits), but collapsed folders will be skipped (this makes sense only
on AMS 2.xx). This option obviously has not any sense when b0 is set.
Summary, the valid combination of flag bits are 000000, 000001, 000010, 000100, 000110,
001000, 001001, 001010, 001100, 001110, 010001, 100000, 100010, 100100, 100110, 101000,
101010, 101100 and 101110.
SymFindFirst returns the pointer to the symbol entry in the VAT, or NULL
if there is no any symbols which satisfies given requirements. Here is an example how to
(legally) create a list of all variable names in the main folder:
counter = 0;
SymPtr = SymFindFirst ($(main), 1);
while (SymPtr)
{
strcpy (names[counter++], SymPtr->name);
SymPtr = SymFindNext ();
}
If you want to create a list of all folder names, simply change
SymPtr = SymFindFirst ($(main), 1);
in the previous example to
SymPtr = SymFindFirst (NULL, 0);
NOTE: Since this routine and subsequent calls to SymFindNext and
SymFindPrev return direct pointers to the symbol table, anything
that would cause heap compression will cause the results to be invalid or may lock-up the
system. In other words, heap compression will invalidate the pointers returned necessitating
another call to SymFindFirst. That's why locking the folder table
(using FolderOp) during traversing through the VAT table is highly
recommended.
SYM_ENTRY *SymFindNext (void);
Finds a next entry in the VAT table.
SymFindNext searches for a next symbol entry in the VAT table after previous calling of
SymFindFirst. The exact behaviour of SymFindNext depends of the
parameters given with SymFindFirst. See description of
SymFindFirst for more info and examples of usage.
SymFindNext returns the pointer to the symbol entry in the VAT,
or NULL if there is no more entries in the VAT which satisfies given
requirements.
SYM_ENTRY *SymFindPrev (void);
Finds a previous entry in the VAT table.
SymFindPrev is very similar to SymFindNext, but instead of the
next entry in the VAT, SymFindPrev searchs for a previous entry in the VAT.
Normally the only routine used with SymFindFirst is
SymFindNext, but this routine allows a program to traverse the
symbol table in both directions. For example, VAR-LINK dialog uses this routine to present a
scrollable list of all symbols without having to maintain a separate in-memory list.
HSym MakeHSym (HANDLE FldHandle, const SYM_ENTRY *SymPtr);
Makes a HSym structure.
MakeHSym is an internal function, used very often in other TIOS routines. It converts the
VAT symbol entry pointed to by SymPtr which belongs to the folder associated with
handle FldHandle to the HSym structure. As HSym-s are basically a
combination of the folder’s handle and the offset of a symbol into that
folder, they are valid until a symbol is added or removed from the folder
they belong to. Dereferencing them with DerefSym produces a direct
pointer to the symbol entry, but such pointer are not valid after a heap compression is done.
The main usage of MakeHSym is when you need to preserve a pointer to the symbol entry after
a heap compression, like in following example:
hsym = MakeHsym (FldHandle, SymPtr);
// Something that may cause heap compression...
SymPtr = DerefSym (hsym);
In this example, an eventual heap compression would cause the pointer to be invalid
since it is a direct pointer into memory. So the SymPtr is converted to a
HSym structure with MakeHsym (along with the handle of the folder that the
symbol belongs to). After the code that may cause heap compression is
executed, the HSym is converted back into a SYM_ENTRY pointer with
DerefSym.
Checks whether a name is the name of the main folder.
IsMainFolderStr returns TRUE if Name is the string "main",
else returns FALSE.
Locks or unlocks a folder table.
FolderOp locks or unlocks a folder table which name is determined by SymName.
Returns TRUE if the operation was successful, else returns FALSE.
Parameter Flags may have following values (these constants are defined in
enum FolderOpFlags):
FOP_UNLOCK | Unlocks a folder table |
FOP_LOCK | Locks a folder table |
FOP_ALL_FOLDERS | Locks/unlocks all folder tables (SymName is ignored);
this value should be ORed with one of FOP_UNLOCK or FOP_LOCK |
By locking the folder table, you may be sure that a dereferenced pointer to the table
will remain valid even after a lot of heap memory allocations (i.e. a garbage collection
will not move the table through a memory).
NOTE: To lock the "home" folder (this is a pseudo-folder which contains all other folders in
itself, i.e. this is the table of folders), you need to know that its name consist only of the
character with code 0x7F (diamond). So, you can use
FolderOp ($(\x7F), FOP_LOCK);
to do this.
Returns an actual folder name during browsing through the VAT table.
This routine is used only when you search the complete VAT table using functions SymFindFirst,
SymFindNext and SymFindPrev with b2 bit
in Flags set. Each time when the folder is encountered in the VAT table, TIOS stores
its name in an internal buffer. Later, when you traverse through the variable part of the VAT
table, you can call this routine to retrieve stored folder name, i.e. to get the name of the
folder for the symbol just returned. Under any other conditions, SymFindFolderName just returns
a pointer to the string "main".
NOTE: The description of this routine in TIGCCLIB releases prior to 2.3 was not wrong, but
was so confuse that nearly nobody was able to deduce what is purpose of it.
Copies a symbol name.
SymCpy copies at most 8 characters from string src to dest, then fills
rest of the dest up to 8 bytes, so dest must be at least 8 bytes
long. It seems that calling this function is equal to
strncpy (dest, src, 8);
except in the fact that function SymCpy is void.
See strncpy for more info.
Copies a symbol name with putting zero byte at the end.
SymCpy0 first performs SymCpy, then puts the zero byte in
ninth byte of the string pointed to by dest (i.e. in dest[8]). So,
dest must be at least 9 bytes long.
Compares two symbol names.
SymCmp compares two symbol names by comparing at most 8 characters starting from
addresses pointed to by s1 and s2. Returns the same result as
strcmp. It seems that calling this function is equal to
strncmp (s1, s2, 8);
See strncmp for more info.
Macro constructors
The most of TIOS functions for manipulating with symbols does not accept ordinary C strings
as filenames. Instead, symbol name is a sequence of characters which starts with zero character
('\0') and terminates with zero character too, and TIOS routines for VAT handling needs a
pointer to the TERMINATING zero byte as an input argument, which is a bit twisty.
For example, to search for a symbol named "tetris", instead of
hsym = SymFind ("tetris");
you must do the following:
hsym = SymFind ("\0tetris"+7);
To make this job easier, a constructor macro $ is implemented, so you may simply do
hsym = SymFind ($(tetris));
Constructor $ is implemented as
#define $(s) (("\0"#s)+sizeof(#s))
So, $(tetris)
expands to
(("\0""tetris")+sizeof("tetris"))
which is, in fact, the same as
"\0tetris"+7
. Of course, constructor $ is valid only when the symbol name
is a constant. If the symbol name is variable, you must to do manual string manipulations using
strcpy and strlen to
convert a standard C string to the TIOS symbol name. For example, assuming that "Filename"
is a standard C filename string and "TIOSname" is a char buffer, you can do the following:
TIOSname[0] = 0;
hsym = SymFind (strcpy (TIOSname + 1, Filename) + strlen (Filename));
Constants and predefined types
Bool is enumerated type for describing true or false values. It is defined as
enum Bool {FALSE, TRUE};
FolderOpFlags is enumerated type for describing possible options which are used in
FolderOp function. It is defined as
enum FolderOpFlags {FOP_UNLOCK = 0, FOP_LOCK = 1, FOP_ALL_FOLDERS = 0x80};
CompatFlags is enumerated type for describing possible compatibility flags in
SYM_ENTRY structure. It is defined as
enum CompatFlags {CF_NONE = 0, CF_CONVERT = 1, CF_ENHANCED = 2, CF_NEW = 3};
FolderStats is enumerated type for describing possible results of FolderFind
function. It is defined as
enum FolderStats {MAIN_FOLDER = 2, FOLDER_TABLE = 3, NOT_FOUND = 4,
BAD_FOLDER = 5};
SymFlags is enumerated type for easier accessing to various flags in VAT symbol entries which
are represented by SYM_ENTRY structure. It is defined as
enum SymFlags {SF_GREF1 = 0x0001, SF_GREF2 = 0x0002,
SF_STATVAR = 0x0004, SF_LOCKED = 0x0008, SF_HIDDEN = 0x0010,
SF_OPEN = 0x0010, SF_CHECKED = 0x0020, SF_OVERWRITTEN = 0x0040,
SF_FOLDER = 0x0080, SF_INVIEW = 0x0100, SF_ARCHIVED = 0x0200,
SF_TWIN = 0x0400, SF_COLLAPSED = 0x0800, SF_LOCAL = 0x4000,
SF_BUSY = 0x8000};
See SYM_ENTRY for more info.
HANDLE is a type which represents handles associated to allocated memory
blocks. It is defined as
typedef unsigned short HANDLE;
H_NULL is a null-handle defined as a constant with value 0.
NULL is a null-pointer value, defined as (void *) 0.
HSym is a structure which contains the handle of the variable table list which belongs to the
folder in which the symbol is located, and the offset from the beginning ot the list to the
actual VAT symbol entry. HSym-s are used as a safe and efficient method for passing variable
references around the system, so that there are no probems after the garbage collection (i.e.
the heap compression). In other words, HSym-s stay valid even after the heap compression.
Note however that HSym-s may become invalid whenever a new symbol is added or a previous one
is removed from the VAT table.
HSym is defined as
typedef struct
{
HANDLE folder;
unsigned short offset;
} HSym;
HS_NULL is a null symbol, defined as (HSym) {0, 0}. Many TIOS functions returns such symbol
in a case of error. Note that you can't check whether a some variable is HS_NULL using
"==" operator because HS_NULL is not scalar, i.e. you can't
write something like
if (hs == HS_NULL) ...
Instead, check folder field of HSym structure: if it is zero,
the whole structure is HS_NULL, because TIOS never creates HSym
structures in which folder field is zero, and offset field is non-zero.
SYM_ENTRY is a structure which represents the VAT symbol entry. It is defined as
typedef struct
{
char name[8];
unsigned short compat;
union
{
unsigned short flags_n;
struct
{
unsigned short busy : 1, local : 1, flag1_5 : 1, flag1_4 : 1,
collapsed : 1, twin : 1, archived : 1, in_view : 1;
unsigned short folder : 1, overwritten : 1, checked : 1, hidden : 1,
locked : 1, statvar : 1, graph_ref_1 : 1, graph_ref_0 : 1;
} bits;
} flags;
unsigned short handle;
} SYM_ENTRY;
Principally, SYM_ENTRY consists of the symbol name, the flags and the handle associated with the symbol.
Flags are defined as union, so you can access to all flags together using field flags_n
(in such case, constants defined in enum SymFlags may be useful for
bit masking), or access to individual flags (which are defined as bit fields) using field bits.
Some flags are unused, and some flags has unknown meaning. At the moment, known flags are:
locked (set for locked symbols), hidden (set for symbols which are hidden for
the TI-Basic; in fact, "hidden" files are files which are currently opened, i.e. in-use files),
checked (set for symbols which are checked in VAR-LINK), folder (set for folder entries),
collapsed (set for collapsed folders; this has sense only on AMS 2.xx),
archived (set for archived symbols), twin (set for
twin symols, see SymAddTwin), and local (set for local symbols).
For example, if "SymPtr" is the pointer to the VAT symbol entry, the following command makes
this symbol invisible for TIOS:
SymPtr->flags.bits.hidden = 1;
Each symbol has also associated compatibility flag (field compat). It determines how
the symbol will behave during sending to unexpanded (non-Plus) TI-92. There are four possible values
of the compatibility flag (these constants are defined in enum CompatFlags):
CF_NONE | Sends immediately |
CF_CONVERT | Converts and sends |
CF_ENHANCED | An enhanced token - may or may not work |
CF_NEW | Will not be send |
A compatibilty number of CF_CONVERT or CF_NEW is determined from symbols context.
CF_ENHANCED is related mainly for internal tokens, which does not appear in final
results and programs.
Here is the list of token tags (see Tags) which belong
to CF_CONVERT, CF_ENHANCED and CF_NEW categories:
Convert: |
LOCALVAR_TAG |
Enhanced: |
_VAR_Q_TAG, PN_INFINITY_TAG, tag 0x5F (internal), START_TAG, ISTORE_TAG, ANS_TAG,
ENTRY_TAG, MATRIX_TAG, ERROR_MSG_TAG, tags 0xF5, 0xF6 and 0xF7 (internal)
|
New: |
PART_TAG, PN1_TAG, PN2_TAG, EIGVC_TAG, EIGVL_TAG, DASH_TAG, DESOLVE_TAG, FDASH_TAG,
ASM_TAG, ISPRIME_TAG, OTH_TAG, ROTATE_TAG, PARENTH_START_TAG, PARENTH_END_TAG,
MAT_START_TAG, MAT_END_TAG, LIST_START_TAG, LIST_END_TAG, COMMA_TAG, SEMICOLON_TAG,
COMPLEX_ANGLE_TAG, SINGLE_QUOTE_TAG, QUOTE_TAG, POLCPLX_TAG, TMPCNV_TAG,
DELTA_TMPCNV_TAG, GETUNITS_TAG, SETUNITS_TAG, BIN_TAG, HEX_TAG, INT2BIN_TAG, INT2DEC_TAG,
INT2HEX_TAG, DET_TOL_TAG, REF_TOL_TAG, RREF_TOL_TAG, SIMULT_TOL_TAG, GETCONFG_TAG,
V_AUGMENT_TAG, EYE_PSI_TAG, TPLOT_TAG, DIFTOL_TAG, ZEYE_PSI_TAG, T0_TAG, DTIME_TAG,
NCURVES_TAG, FLDRES_TAG, ESTEP_TAG, ZT0DE_TAG, ZTMAXDE_TAG, ZTSTEPDE_TAG, ZTPLOTDE_TAG,
NCONTOUR_TAG, DISPHOME_ITAG, EXEC_ITAG, ARCHIVE_ITAG, UNARCHIV_ITAG, LU_ITAG, QR_ITAG,
BLDDATA_ITAG, DRWCTOUR_ITAG, NEWPROB_ITAG, SINREG_ITAG, LOGISTIC_ITAG, CUSTMON_ITAG,
CUSTMOFF_ITAG, SENDCHAT_ITAG
|