Topic : The ATARI Compendium
Author : Scott Sanders / JAY Software
Version : 1.25 (20/6/2003)
Subject : Documentation
Nodes : 1117
Index Size : 32614
HCP-Version : 6
Compiled on : Atari
@charset : UTF-8
@lang : en
@default :
@help : %About
@options : +g -i -t4 +y +z
@width : 100
View Ref-FileLoadable DevicesMiNT contains a number of built-in devices and also supports loadable
device drivers. Current versions of MiNT may contain any of the following
devices:
Device Filename Device
CENTR Centronics Parallel Port
MODEM1 Modem Port 1
MODEM2 Modem Port 2
SERIAL1 Serial Port 1
SERIAL2 Serial Port 2
MIDI MIDI ports
PRN PRN: device (usually the Centronics Parallel Port)
AUX AUX: device (usually the RS232 Port)
CON Current Terminal
TTY Current Terminal (same as CON)
STDIN Current File Handle 0 (standard input)
STDOUT Current File Handle 1 (standard output)
STDERR Current File Handle 2 (standard error)
CONSOLE Physical Console (keyboard/screen)
MOUSE Mouse (system use only)
NULL NULL device
AES_BIOS AESBIOS Device (system use only)
AES_MT AES Multitasking Device (system use only)
Each of these devices is represented by a filename (as shown in the table
above) in the 'U:\DEV\' directory. Using standard GEMDOS calls (ex: Fread()and Fwrite()) on these files yields the same results as accessing the
device directly. New devices, including those directly accessible by the
BIOS, may be added to the system with the Dcntl() call using a parameter
of DEV_INSTALL, DEV_NEWBIOS, or DEV_NEWTTY. See the Dcntl() call for details.
MiNTversions 1.08 and above will automatically load device drivers with
an extension of '.XDD' found in the root or '\MULTITOS' directory. '.XDD'
files are special device driver executables which are responsible for
installing one (or more) new devices. MiNT will load the file and JSR to
the first instruction in the TEXT segment (no parameters are passed). The
device driver executable should not attempt to Mshrink() or create a stack
(one has already been created).
The '.XDD' may then either install its device itself with Dcntl() and
return DEV_SELFINST (1L) in register D0 or return a pointer to a DEVDRVstructure to have the MiNT kernel install it (the 'U:\DEV\' filename will
be the same as the first eight characters of the '.XDD' file). If for some
reason, the device can not be initialized, 0L should be returned in D0.
When creating a new MiNT device with Dcntl( DEV_INSTALL, devname,
&dev_descr ) the structure dev_descr contains a pointer to your DEVDRVstructure defined as follows:
typedef struct devdrv
{
LONG (*open)( FILEPTR *f );
LONG (*write)( FILEPTR *f, char *buf, LONG bytes );
LONG (*read)( FILEPTR *f, char *buf, LONG bytes );
LONG (*lseek)( FILEPTR *f, LONG where, LONG whence );
LONG (*ioctl)( FILEPTR *f, WORD mode, VOIDP buf );
LONG (*datime)( FILEPTR *f, WORD *timeptr, WORD rwflag );
LONG (*close)( FILEPTR *f, WORD pid );
LONG (*select)( FILEPTR *f, LONG proc, WORD mode );
LONG (*unselect)( FILEPTR *f, LONG proc, WORD mode );
LONG reserved[3];
} DEVDRV;
Each of the assigned members of this structure should point to a valid
routine that provides the named operation on the device. The routine must
preserve registers D2-D7 and A2-A7 returning its completion code in D0. No
operating system TRAPs should be called from within these routines,
however, using the vector tables provided in the kerinfo structure
returned from the Dcntl() call, GEMDOS and BIOS calls may be used. The
specific function that each routine is responsible for is as follows:
Member Meaning
open This routine is called by the MiNT kernel after a FILEPTR structure has been created for a file determined to be
associated with the device. The routine should perform whatever
initialization is necessary and exit with a standard GEMDOS completion code. This routine is responsible for validating the
sharing mode and other file flags to verify that the file may be
legally opened and should respond with an appropriate error code
if necessary.
write This routine should write bytes number of BYTEs from buf to the
file specified in FILEPTR. If the file pointer has the O_APPEND
bit set, the kernel will perform an lseek() call to the end of
the file prior to calling this function. If the lseek()/write()
series of calls does not guarantee that data will be written at
the end of a file associated with your device, this function
must ensure that the data specified is actually written at the
end of the file. This function should return with a standard
GEMDOS error code or the actual number of BYTEs written to the
file when complete.
read This routine should read bytes number of BYTEs from the file
specified in FILEPTR and place them in the buffer buf. This
function should return with a standard GEMDOS error code or the
actual number of bytes read by the routine.
lseek This routine should move the file position pointer to the
appropriate location in the file as specified by the parameter
where in relation to the seek mode whence. Seek modes are the
same as with Fseek(). The routine should return a GEMDOS error
code or the absolute new position from the start of the file if
successful.
ioctl This routine is called from the system's perspective as Fcntl() and is used to perform file system/device specific functions. At
the very least, your device should support FIONREAD, FIONWRITE,
and the file/record locking modes of Fcntl(). The arg parameter
of Fcntl() is passed as buf.
datime This routine is used to read or modify the date/time attributes
of a file. timeptr is a pointer to two LONGs containing the time
and date of the file respectively. These LONGs should be used to
set the file date and time if rwflag is non-zero or filled in
with the file's creation date and time if rwflag is 0. This
function should return with a standard GEMDOS error code or E_OK (0) if successful.
close This routine is used by the kernel to close an open file. Be
aware that if f->links is non-zero, additional processes still
have valid handles to the file. If f->links is 0 then the file
is really being closed. pid specifies the process closing the
file and may not necessarily be the same as the process that
opened it. Device drivers should set the O_LOCK bit on f->flag
when the F_SETLK or F_SETLKW ioctl() call is made. This bit can
be tested for when a file is closed and all locks on all files
associated with the same physical file owned by process pid
should be removed. If the file did not have any locks created on
it by process pid, then no locks should be removed. This routine
should return with a standard GEMDOS error code or E_OK (0) if
successful.
select This routine is called when a call to Fselect() names a file
handled by this device. If mode is O_RDONLY then the select is
for reading, otherwise, if mode is O_WRONLY then it is for
writing. If the user Fselect()'s for both reading and writing
then two calls to this function will be made. The routine should
return 1L if the device is ready for reading or writing (as
appropriate) or it should return 0L and arrange to 'wake up'
process proc when I/O becomes possible. This is usually
accomplished by calling the wakeselect() member function of the
kernel structure. Note that the value in proc is not the same as
a PID and is actually a pointer to a PROC structure private to
the MiNT kernel.
unselect This routine is called when a device waiting for I/O should no
longer be waited for. The mode and proc parameters are the same
as with select(). As with select(), if neither reading nor
writing is to be waited for, two calls to this function will be
made. This routine should return a standard GEMDOS error code or
E_OK (0) if successful.
The FILEPTR structure pointed to by a parameter of each of the above
calls is defined as follows:
typedef struct fileptr
{
WORD links;
UWORD flags;
LONG pos;
LONG devinfo;
fcookie fc;
struct devdrv *dev;
struct fileptr *next;
} FILEPTR;
The members of FILEPTR have significance as follows:
Member Meaning
links This member contains a value indicating the number of copies of
this file descriptor currently in existence.
flags This member contains a bit mask which indicates several
attributes (logically OR'ed together) of the file as follows:
Name Mask Meaning
O_RDONLY 0x0000 File is read-only.
O_WRONLY 0x0001 File is write-only.
O_RDWR 0x0002 File may be read or written.
O_EXEC 0x0003 File was opened to be executed.
O_APPEND 0x0008 Writes start at the end of the file.
O_COMPAT 0x0000 File-sharing compatibility mode.
O_DENYRW 0x0010 Deny read and write access.
O_DENYW 0x0020 Deny write access.
O_DENYR 0x0030 Deny read access.
O_DENYNONE 0x0040 Allow reads and writes.
O_NOINHERIT 0x0080 Children cannot use this file.
O_NDELAY 0x0100 Device should not block for I/O on this file.
O_CREAT 0x0200 File should be created if it doesn't exist.
O_TRUNC 0x0400 File should be truncated to 0 BYTEs if it
already exists.
O_EXCL 0x0800 Open should fail if file already exists.
O_TTY 0x2000 File is a terminal.
O_HEAD 0x4000 File is a pseudo-terminal "master."
O_LOCK 0x8000 File has been locked.
pos This field is initialized to 0 when a file is created and should
be used by the device driver to store the file position pointer.
devinfo This field is reserved for use between the file system and the
device driver and may be used as desired. The exception to this
is if the file is a TTY, in which case devinfo must be a pointer
to a tty structure.
fc This is the file cookie for the file as follows:
typedef struct f_cookie {
FILESYS *fs;
UWORD dev;
UWORD aux;
LONG index;
} fcookie;
fs is a pointer to the file system structure responsible for this
device. dev is a UWORD giving a useful device ID (such as the
Rwabs() device number). The meaning of aux is file system
dependent. index should be used by file systems to provide a
unique means of identifying a file.
dev This is a pointer to the DEVDRV structure of the device driver
responsible for this file.
next This pointer may be used by device drivers to link copies of
duplicate file descriptors to implement file locking or sharing
code.
Upon successful return from the Dcntl() call, a pointer to a kerinfostructure will be returned. The kerinfo structure is defined below:
typedef LONG (*Func)();
struct kerinfo{
WORD maj_version;
WORD min_version;
UWORD default_mode;
WORD reserved1;
Func *bios_tab;
Func *dos_tab;
VOID (*drvchng)( UWORD dev );
VOID (*trace)( char *, ... );
VOID (*debug)( char *, ... );
VOID (*alert)( char *, ... );
VOID (*fatal)( char *, ... );
VOIDP (*kmalloc)( LONG size );
VOID (*kfree)( VOIDP memptr );
VOIDP (*umalloc)( LONG size );
VOID (*ufree)( LONG memptr );
WORD (*strnicmp)( char *str1, char *str2, WORD maxsrch );
WORD (*stricmp)( char *str1, char *str2 );
char * (*strlwr)( char *str );
char * (*strupr)( char *str );
WORD (*sprintf)( char *strbuf, const char *fmtstr, ... );
VOID (*millis_time)( ULONG ms, WORD *td );
LONG (*unixtim)( UWORD time, UWORD date );
LONG (*dostim)( LONG unixtime );
VOID (*nap)( UWORD n );
VOID (*sleep)( WORD que, WORD cond );
VOID (*wake)( WORD que, WORD cond );
VOID (*wakeselect)( LONG proc );
WORD (*denyshare)( FILEPTR *list, FILEPTR *f );
LOCK * (*denylock)( LOCK *list, LOCK *new );
LONG res2[9];
};
The members of the kerinfo structure are defined as follows:
Member Meaning
maj_version This WORD contains the kernel version number.
min_version This WORD contains the minor kernel version number.
default_mode This UWORD contains the default access permissions for a file.
reserved1 Reserved.
bios_tab This is a pointer to the BIOS function jump table. Calling
bios_tab[0x00]() is equivalent to calling Getmpb() and is
the only safe way from within a device driver or file
system.
dos_tab This is a pointer to the GEMDOS function jump table. Calling
dos_tab[0x3D]() is equivalent to calling Fopen() and is the
only safe way from within a device driver or file system.
drvchng This function should be called by a device driver if a media
change was detected on the device during an operation. The
parameter dev is the BIOS device number of the device.
trace This function is used to send information messages to the
kernel for debugging purposes.
debug This function is used to send error messages to the kernel
for debugging purposes.
alert This function is used to send serious error messages to the
kernel for debugging purposes.
fatal This function is used to send fatal error messages to the
kernel for debugging purposes.
kmalloc Use this internal heap memory management function to
allocate memory.
kfree Use this internal heap memory management function to free
memory allocated with kmalloc().
umalloc Use this internal heap memory management function to
allocate memory and attach it to the current process. The
memory will be released automatically when the current
process exits.
ufree Use this internal heap memory management function to
allocate memory allocated with ufree().
strnicmp This function compares maxsrch characters of str1 to str2
and returns a negative value if str1 is lower than str2,
a positive value if str1 is higher than str2, or 0 if they
are equal.
stricmp This function compares two NULL terminated strings, str1 to
str2, and returns a negative value if str1 is lower than
str2, a positive value if str1 is higher than str2, or 0 if
they are equal.
strlwr This function converts all alphabetic characters in str to
lower case.
strupr This function converts all alphabetic characters in str to
upper case.
sprintf This function is the same as the 'C' library sprintf()
function except that it will only convert SPRINTF_MAX
characters (defined in TOSDEFS.H).
millis_time This function converts the millisecond time value in ms to
a GEMDOS time in td[0] and date in td[1].
unixtim This function converts a GEMDOS time and date in a UNIX
format LONG.
dostim This function converts a UNIX format LONG time/date value
into a GEMDOS time/date value. The return value contains the
time in the upper WORD and the date in the lower WORD.
nap This function causes a delay of n milliseconds.
sleep This function causes the current process to sleep, placing
it on the system que que until condition cond is met.
wake This function causes all processes in que que, waiting for
condition cond, to be woken.
wakeselect This function wakes a process named by the code proc
currently doing a select operation.
denyshare This function determines whether the sharing mode of f
conflicts with any of the files given in the linked list
list.
denylock This function determines whether a new lock new conflicts
with any existing lock in the linked list list. The LOCK structure is used internally by the kernel and is defined
as follows:
typedef struct ilock
{
FLOCK l;
struct ilock *next;
LONG reserved[4];
} LOCK;
l is the structure actually containing the lock data (as
defined in Fcntl()). next is a pointer to the next LOCK structure in the linked list or NULL if this is the last lock.
reserved is a pointer to four LONGs currently reserved.
res2 These longwords are reserved for future expansion.