/*------------------------ VIS_LIST.TXT ------------------------*/ /* */ /* This file contains the VISIONS List Library Manual */ /* */ /* Copyright 1990 Dan Vogel & David Bernazzani */ /* */ /* Date Initials Comments */ /* */ /* 03/13/90 DCV Initial Release 0.00. */ /* 07/24/90 DCV Release 1.2. */ /*--------------------------------------------------------------*/ Overview The VISIONS list library is a simple library, written in C, to provide generic list handling on PC/XT/AT class machines. The library was originally written in Microsoft C 5.1. The VISIONS list library uses the VISIONS Window library. The list library, although simple, provides the programmer an easy way of handling lists of any type of data structure. The list library provides the programmer with the ability to create lists, sort lists, add items to lists, remove items from lists, and display list items. All this is done with a minimum of programmer knowledge of the actual structure of the list. In fact, the definition of the list structure is not made available to the library user, in order to abstract away these complications. Theory of Operation While it is not necessary for the programmer to know the details of the list structure, a brief description of this structure will help to explain some of the list routines. A list is composed of three separate structures in VISIONS, a list head, list links, and list elements. A list head is used to define the start of a list as well as some of the operations that may be performed upon this list. A list link is a pointer structure used to connect list elements together in a doubly linked chain. Finally a list element is the data of which the programmer wishes to create a list. The list element(s) may be any type of data, although all data is treated as an unsigned character pointer by VISIONS. The list head and list links are never directly manipulated by the programmer, only by VISIONS, although the programmer must keep a pointer reference to define the list he wishes to operate upon at any given time. A list might appear as below: LIST_HEAD: +------------+ |List delete | |List compare| |List display| |List Pointer|-----+ +------------+ | LIST_LINK: LIST_LINK: +->+--------+ +--------+ |Next |-------->|Next |----> etc. NULL<--|Last |<--------|Last | |Element |--+ |Element |--+ +--------+ | +--------+ | | | | ELEMENT: | ELEMENT: +->+------+ +->+------+ |"One" | |"Two" | +------+ +------+ Storage for list heads and list links is allocated from the heap. Thus a list's maximum length is bounded by the availability of heap storage, not by the size of any preallocated array. Since list links may be frequently allocated and deallocated, the VISIONS list library performs its own garbage collection for list links. This allows previously allocated and deallocated list links to be reused without be returned to the heap. This helps prevents extreme memory fragmentation. The following is a brief overview of the operation of the list library routines. This is intended to help the user to understand the library's operation better, so that it may be used more effectively. One key point to remember in reviewing these routines is that list elements are almost always manipulated by list link pointers, not by pointers to the actual list elements. As an example, using the VISIONS routine ListTop of the above list structure would return a pointer to the first list link (which in turn points to the first element "One"), not to the first list element. Once your list manipulation is complete, you may recover your list element data by using the routine GetListItem. This abstracts list manipulation apart from data manipulation. The VISIONS list system is intended to create and use lists of any type of items. List functions may be broken up into the following groups. List Definition: List_Define - Define a list header with operations that may be performed on the list. List Building: List_Add - Add an element to the list before the passed list link pointer. List_Append - Append a new element to the end of the list. List Item Selection: List_Find - Find the list link associated with a list element. List_Bottom - Return pointer to list link at end of list. List_Last - Return pointer to list link preceeding passed link. List_Next - Return pointer to list link following passed link. List_Nth - Return pointer to nth list link in list. List_Top - Return poiinter to list link at start of list. List Display: List_Display - Display all elements in passed list in the defined window, as formatted by list display routine. List_DisplayItem - Format a list element into a buffer for display. List Deletion: List_Delete - Delete a list and all of its contents. List_DeleteItem - Delete a list link and its element from its list. List Miscellaneous: List_Count - Count the number of elements in the passed list. List_GetItem - Return a pointer to the list element held by the passed list link. List_RemoveItem - Remove a list link and its element from its list without deleting the element. The link is returned to the free memory chain. List_Select - Display the passed list in the defined window, and allow the user to select an item from the list. Lists larger than the window are scrolled. List_Sort - Sort a list according to a passed comparison routine. The next section defines these routines in greater detail. Routine Definitions In order to use the below routines you must include the file "USERLIST.H" in your source code with the following statement. #include "USERLIST.H" This will automatically include the window definitions files at the same time. Examples of the use of these routines are available in the VISIONS demonstration program, in the file DEMOLIST.C. If you are compiling a program written for VISIONS 1.0 and do not wish to modify the routine names in your source, add the following statement to provide name conversions. #include "LISTCONV.H" /*------------------------------------------------------------------------*/ List_Add Purpose: This routine inserts a new item into the current list before the list item pointer passed. Calling Sequence: status = List_Add(list_root, list_ptr, new_item); Inputs: LIST_HEAD *list_root; - This is the head of the list added to. LIST_LINK *list_ptr; - This is a pointer to insert the item before. UBYTE *new_item; - This is a pointer to the item to be inserted in the list. Outputs: WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. LIST_ERR_BAD_LINK Pointer to link passed is invalid. As returned by called routines. Functions called: None. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Append Purpose: This routine adds an item to the end of the list. Calling Sequence: status = List_Append(list_top, new_item); Inputs: LIST_HEAD *list_top; - This is a pointer to the head of the list to append to. UBYTE *new_item; - This is the item to be appended to the list. Outputs: WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: None. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Bottom Purpose: This routine passes back a pointer to the last link in the passed list. Calling Sequence: status = List_Bottom(list_ptr, bot_link); Inputs: LIST_HEAD *list_ptr; - This is a pointer to the list head. Outputs: LIST_LINK **bot_link; - This is the returned pointer to the last element of the passed list. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Top, List_Next. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Count Purpose: This routine passes back a count of items in the passed list. Calling Sequence: status = List_Count(list_ptr); Inputs: LIST_HEAD *list_ptr; - This is a pointer to the list head to be counted. Outputs: WORD status; - This is the result of the function. Possible values are: >=0 Success, this is the count of items in the list. LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Top, List_Next. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Define Purpose: This routine initializes a new list structure, and allocates space for it. Calling Sequence: status = List_Define(new_list,compare_f,delete_f,display_f); Inputs: The following three functions are passed to this routine to be stored as part of the list defining the operations that can be performed on this list. These operations include comparing two items in the list, deleting a list item, and generating a displayable buffer from a list item. WORD (*compare_f)(UBYTE *,UBYTE *); WORD (*delete_f)(UBYTE *); WORD (*display_f)(UBYTE *,TEXT *); Outputs: LIST_HEAD **new_list; - This is the head of the new list created. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success As returned by called routines. Functions called: None. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Delete Purpose: This routine deletes an entire list, releasing its storage back to the heap. Calling Sequence: status = List_Delete(del_list); Inputs: LIST_HEAD *del_list; - This is a pointer to the list to be deleted. Outputs: WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Top, List_DeleteItem. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_DeleteItem Purpose: This routine removes a link from a list, releases the link to the free link list, and passes the link's item pointer to the list delete routine. Calling Sequence: status = List_DeleteItem(list_ptr, remove_item); Inputs: LIST_HEAD *list_ptr; - This is a pointer to the list to remove the item from. UBYTE *remove_item; - This is a pointer to the item to be deleted from the list. Outputs: WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Find, . /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Display Purpose: This routine displays the passed list in the specified window. Calling Sequence: status = List_Display(topy, col, height, width, bkcol, txtcol, border, title, d_list) Inputs: UBYTE topy, col, height, width; - These are the coordinates of the window in which to display the list. DWORD bkcol, txtcol; - These are the colors to use for the window. UBYTE border; - This is the border type to use (NOBORDER,SINGLEBORDER, or DOUBLEBORDER). TEXT *title; - This is the title to display in the window (or NULL). LIST_HEAD *d_list; - This is a pointer to the list to be displayed. Outputs: WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: Window_Define, Window_Display, Comp_GetAnyKey, Window_Mesg, Window_Remove, Window_Delete. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_DisplayItem Purpose: This routine generates a displayable buffer of the item in the passed list link pointer using the list's display routine. Calling Sequence: status = List_DisplayItem(list_ptr, disp_link, buffer); Inputs: LIST_HEAD *list_ptr; - This is the list containing the item to be displayed. LIST_LINK *disp_link; - This is the link of the item to be displayed. Outputs: TEXT *buffer; - This is the buffer in which the displayable string is placed. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. LIST_ERR_BAD_LINK Pointer to link passed is invalid. As returned by called routines. Functions called: /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Find Purpose: This routine finds the list pointer in a list that holds the passed item pointer. Calling Sequence: status = List_Find(list_ptr, find_item, list_fnd); Inputs: LIST_HEAD *list_ptr; - This is the list to be searched. UBYTE *find_item; - This is the item to be found. Outputs: LIST_LINK **list_fnd; - This is a pointer to the pointer to the found item's link. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_ITEM_NOT_FOUND Didn't find the item in the list. LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Top, List_Next, . /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_GetItem Purpose: This routine returns a pointer to the item contained in the passed list link. Calling Sequence: status = List_GetItem(list_ptr, new_item); Inputs: LIST_LINK *list_ptr; - This is a pointer to the list link to get the item pointer from. Outputs: UBYTE **new_item; - This is a pointer to the pointer to hold the returned item pointer. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_LINK Pointer to link passed is invalid. Functions called: None. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Last Purpose: This routine passes back a pointer to the previous link in the passed list. Calling Sequence: status = List_Last(curr_link, last_link); Inputs: LIST_LINK *curr_link; - This is a pointer to the current link. Outputs: LIST_LINK **last_link; - This is the returned pointer to the link preceeding the current link. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_LINK Pointer to link passed is invalid. Functions called: None. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Next Purpose: This routine passes back a pointer to the next link in the passed list. Calling Sequence: status = List_Next(curr_link, next_link); Inputs: LIST_LINK *curr_link; - This is a pointer to the current link. Outputs: LIST_LINK **next_link; - This is the returned pointer to the link following the current link. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_LINK Pointer to link passed is invalid. As returned by called routines. Functions called: None. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Nth Purpose: This routine passes back a pointer to the nth link in the passed list, where n ranges from 0 to the number of items in the list minus 1. Calling Sequence: status = List_Nth(list_ptr, list_num, ret_link); Inputs: LIST_HEAD *list_ptr; - This is a pointer to the list head. WORD list_num; - This is the number of the desired item in the list. Outputs: LIST_LINK **ret_link; - This is the returned pointer to the nth element. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_LIST_TOO_SHORT List is not long enough! LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Top, List_Next. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_RemoveItem Purpose: This routine removes a link from a list, and releases the link to the free link list. Calling Sequence: status = List_RemoveItem(list_ptr, remove_item); Inputs: LIST_HEAD *list_ptr; - This is a pointer to the list to remove the item from. UBYTE *remove_item; - This is a pointer to the item to be removed from the list. Outputs: WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Find. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Select Purpose: This routine interfaces with the user to select from the passed list in the specified window. Calling Sequence: status = List_Select(topy, col, height, width, bkcol, txtcol, hbkcol, htxtcol, border, title, d_list, &sel_num); Inputs: UBYTE topy, col, height, width; - These are the coordinates of the window in which to display the list. DWORD bkcol, txtcol, hbkcol, htxtcol; - These are the colors to use for the window. Both normal, and highlighted colors for the cursor. UBYTE border; - This is the border type to use (NOBORDER,SINGLEBORDER, or DOUBLEBORDER). TEXT *title; - This is the title to display in the window. struct list_head *d_list; - This is a pointer to the list to be displayed. Outputs: WORD *sel_num; - This is the selected item number in the list. Possible values range from 0 to the numbver of items in the list minus 1. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_USER_ABORT User exited without selecting. LIST_ERR_EMPTY Passed list is empty, can not select! LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: Window_Define, Window_Display, Window_Remove, Window_Delete, Comp_GetKey. /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Sort Purpose: This routine does a bubble sort of the passed list based upon the passed comparison function. Calling Sequence: status = List_Sort(list_ptr,compare_f); Inputs: LIST_HEAD *list_ptr; - This is a pointer to the list head to be sorted. WORD (*compare_f)(UBYTE *,UBYTE *); - This is the comparison function to be used in the sort. It must return <0 if first argument should preceed second, =0 for two items are equal, and >0 for first item should follow second. Outputs: WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. As returned by called routines. Functions called: List_Top, List_Next, /*------------------------------------------------------------------------*/ /*------------------------------------------------------------------------*/ List_Top Purpose: This routine passes back a pointer to the first link in the passed list. Calling Sequence: status = List_Top(list_ptr, top_link); Inputs: LIST_HEAD *list_ptr; - This is a pointer to the list head. Outputs: LIST_LINK **top_link; - This is the returned pointer to the first element of the passed list. WORD status; - This is the result of the function. Possible values are: LIST_ERR_NO_ERR Success LIST_ERR_BAD_HEAD Pointer to list passed is invalid. Functions called: None. /*------------------------------------------------------------------------*/ Error Codes The following is the list of error codes that can be returned from the VISIONS list library. Errors from calls to the windows library will be passed back unchanged. These error values can be found in the VISIONS window manual. Error Name Value Description. LIST_USER_ABORT -1 User aborted out of list select. LIST_ERR_NO_ERR 0 Success LIST_ERR_BAD_LINK -100 Pointer to list link is bad. LIST_ERR_BAD_HEAD -101 Pointer to list head is bad. LIST_ERR_ALLOC_LINK -102 Out of heap for link allocation. LIST_ERR_ALLOC_LIST -103 Out of heap for head allocation. LIST_ERR_LIST_TOO_SHORT -104 List is shorter than needed item number. LIST_ERR_ITEM_NOT_FOUND -105 Item not found in passed list. LIST_ERR_EMPTY -106 Routine received pointer to empty list.