Sun Microsystems, Inc.
spacerspacer
spacer www.sun.com docs.sun.com |
spacer
black dot
 
 
11.  Configuring STREAMS Drivers and Modules STREAMS Driver Entry Points pts Example  Previous   Contents   Next 
   
 

STREAMS Module Configuration

The following example shows the structures you need if you are working with a module instead of a driver. Notice that a modlstrmod(9S) is used in modlinkage(9S), and fmodsw(9S) points to streamtab(9S) instead of going through dev_ops(9S).


Example 11-2 Module Structures

extern struct streamtab pteminfo;

static struct fmodsw fsw = {
		"ptem",
		&pteminfo,
		D_NEW | D_MP
};

/*
 * Module linkage information for the kernel.
 */
extern struct mod_ops mod_strmodops;

static struct modlstrmod modlstrmod = {
		&mod_strmodops,
		"pty hardware emulator",
		&fsw
};

static struct modlinkage modlinkage = {
		MODREV_1, 
		(void *)&modlstrmod,
		NULL
};

Compilation

Below are some compile, assemble, and link lines for an example driver with two C source files (example_one.c and example_two.c) and an assembly language source file (example_asm.s).

cc -D_KERNEL -c example_one.c
cc -D_KERNEL -c example_two.c
as -P -D_ASM -D_KERNEL -I. -o example_asm.o example_asm.s
ld -r -o example example_one.o example_two.o example_asm.o

Kernel Loading

See Writing Device Drivers for more information on the sequence of installing and loading device drivers. The basic procedure is to copy your driver to /kernel/drv and your module to /kernel/strmod. For drivers run add_drv(1M).


Note - The autoload facility looks for modules to reside in /kernel/strmod. If the object resides elsewhere the module will not be loaded.


Checking the Module Type

Below is sample code that enables a driver to determine if it is running as a regular driver, a module, or a cloneable driver. The open routine returns sflag, which is checked.

	if (sflag == MODOPEN)
 			/* then the module is being pushed */
		else if (sflag == CLONEOPEN)
 			/* then its being opened as a clonable driver */
 	else
 			/* its being opened as a regular driver */

Tunable Parameters

Certain system parameters referred to by STREAMS are configurable when building a new operating system (see the file /etc/system and the SunOS User's Guide to System Administration for further details). These parameters are:

nstrpush

Maximum number (should be at least 8) of modules that can be pushed onto a single stream.

strmsgsz

Maximum number of bytes of information that a single system call can pass to a stream to be placed into the data part of a message (in M_DATA blocks). Any write(2) exceeding this size is broken into multiple messages. A putmsg(2) with a data part exceeding this size fails with ERANGE. If STRMSGSZ is set to 0, the number of bytes passed to a stream is infinite.

strctlsz

Maximum number of bytes of information that a single system call can pass to a stream to be placed into the control part of a message (in an M_PROTO or M_PCPROTO block). A putmsg(2) with a control part that exceeds this size fails with ERANGE.

STREAMS Administrative Driver

The autopush(1M) facility configures the list of modules for a STREAMS device. It automatically pushes a prespecified list (/etc/iu.ap) of modules onto the stream when the STREAMS device is opened and the device is not already open.

The STREAMS Administrative Driver (SAD) (see the sad(7D) man page) provides an interface to the autopush mechanism. System administrators can open the SAD driver and set or get autopush information on other drivers. The SAD driver caches the list of modules to push for each driver. When the driver is opened the stream head checks the SAD's cache to determine if the device is configured to have modules pushed automatically. If an entry is found, the modules are pushed. If the device has been opened but not closed, another open does not cause the list of the prespecified modules to be pushed again.

Three options configure the module list:

  • Configure for each minor device (that is, a specific major and minor device number)

  • Configure for a range of minor devices within a major device

  • Configure for all minor devices within a major device

In addition, when configuring the module list, an optional anchor can be placed within the module list. See "STREAMS Anchors" for more information.

When the module list is cleared, a range of minor devices has to be cleared as a range and not in parts.

Application Interface

The SAD driver is accessed through the /dev/sad/admin or /dev/sad/user node. After the device is initialized, a program can perform any autopush configuration. The program should open the SAD driver, read a configuration file to find out what modules need to be configured for which devices, format the information into strapush structures, and make the SAD_SAP ioctl(2) calls. See the sad(7D) man page for more information.

All autopush operations are performed through SAD_SAP ioctl(2) commands to set or get autopush information. Only the root user can set autopush information, but any user can get the autopush information for a device.

The SAD_SAP ioctl is a form of ioctl(fd, cmd, arg), where fd is the file descriptor of the SAD driver, cmd is either SAD_SAP (set autopush information) or SAD_GAP (get autopush information), and arg is a pointer to the structure strapush.

The strapush structure is shown in the following example:


Example 11-3 strapush Structure

/*
 * maximum number of modules that can be pushed on a
 * stream using the autopush feature should be no greater
 * than nstrpush
 */
#define MAXAPUSH 8

/* autopush information common to user and kernel */

struct apcommon {
   uint     apc_cmd;          /* command - see below */
   major_t  apc_major;        /* major device number */
   minor_t  apc_minor;        /* minor device number */
   minor_t  apc_lastminor;    /* last minor dev # for range */
   uint     apc_npush;        /* number of modules to push */
};

/* ap_cmd - various options of autopush */
#define SAP_CLEAR       0 /* remove configuration list */
#define SAP_ONE         1 /* configure one minor device */
#define SAP_RANGE       2 /* config range of minor devices */
#define SAP_ALL         3 /* configure all minor devices */

/* format of autopush ioctls */
struct strapush {
		struct apcommon sap_common;
		char sap_list[MAXAPUSH] [FMNAMESZ + 1]; /* module list */
};

#define sap_cmd           sap_common.apc_cmd
#define sap_major         sap_common.apc_major
#define sap_minor         sap_common.apc_minor
#define sap_lastminor     sap_common.apc_lastminor
#define sap_npush         sap_common.apc_npush

A device is identified by its major device number, sap_major. The SAD_SAP ioctl(2) has the following options:

 
 
 
  Previous   Contents   Next