Description: Manual Page
Keywords: ss7 ss7/ip ss7 over ip ss7 mtp ss7 sccp ss7 tcap sigtran mtp sccp tcap openss7 acb56 linux telephony pstn linux telephony linux nebs linux compactpci
QI_PUTP
Section: Linux Fast-STREAMS DDI/DKI (9)
Updated: 2008-10-31
Index
Return to Main Contents
NAME
put, qi_putp, qi_putp_t
-
STREAMS driver or module put procedure
SYNOPSIS
-
#include <sys/stream.h>
-
typedef int (*qi_putp_t) (queue_t *q, mblk_t *mp);
ARGUMENTS
- q
pointer to the
queue_t(9)
to which to put a message;
- mp
- pointer to the
mblk_t(9)
message to put to the queue.
INTERFACE
STREAMS.
DESCRIPTION
qi_putp()
is one of 5 principal synchronous entry points into a
STREAMS
driver or module that form part of the definition of the driver or module. The principal entry
points are:
qi_qopen(9),
qi_qclose(9),
qi_qadmin(9),
qi_putp(),
and
qi_srvp(9).
The
qi_putp()
procedure is specified in both the read and write queue
qinit(9)
structure that is associated with each queue in an existing queue pair forming an instance of the
driver or module from the definitions in the module- and driver-defining
streamtab(9)
structure.
The
qi_putp()
procedure is called by
STREAMS
whenever a message is passed from a neighbouring queue procedure with
putnext(9),
or whenever a message is passed to the Stream head write queue or Stream end (driver) read queue
using
put(9).
The
qi_putp()
procedure is the primary mechanism for passing
STREAMS
messages along a Stream.
Although
qi_putp()
is defined to return a value, any returned value is ignored by
STREAMS,
and is not available to the caller of
putnext(9)
nor
put(9),
which return
void.
The arguments passed to the
qi_putp()
procedure are of the same type passed to
put(9)
and
putnext(9);
as follows:
- q
- is a pointer to the
queue(9)
structure representing the read or write queue to which the message is to be passed.
- mp
- is a pointer to the
msgb(9)
structure representing a message reference to a data block,
datab(9)
and associated data buffer, that is to be passed to the queue,
q.
STREAMS
invokes a queue
qi_putp()
procedure as messages are passed to, or along, a Stream with
put(9)
or
putnext(9).
The
qi_putp()
procedure is called in the following circumstances:
- (1)
- put(9)
was called from the Stream head to place a message on the write queue of the driver or module on the
top of the module stack for the Stream.
- (2)
- put(9)
was called from a device driver routine (possibly an interrupt service routine, or soft interrupt
bottom half or tasklet), to place a message on the read queue of the driver.
- (3)
- put(9)
was called from a driver or module
qi_qopen(9)
or
qi_qclose(9)
routine to place a message on the driver or module queue a queue adjacent to the driver or module.
- (4)
- putnext(9)
was called from within a Stream head, driver or module
qi_putp()
or
qi_srvp(9)
procedure to pass a message to a neighbouring queue (adjacent queue, or queue across a multiplexing
driver).
When the
qi_putp()
procedure is invoked for a queue by
STREAMS,
(as a result of proper invocation of
put(9)
or
putnext(9)
from a driver or module), the following conditions prevail:
- (1)
- When invoked using
put(9),
the call will be invoked with a Stream head plumbing read lock for the Stream to which
q
belongs, guaranteeing the validity of any
q_next
pointer within the Stream.
- (2)
- When invoked using
putnext(9),
in the proper fashion,
from another
qi_putp()
or
qi_srvp(9)
procedure, the call will be invoked with a Stream head plumbing read lock for the Stream from which
the call was invoked. When
putnext(9)
is used to pass messages along a single Stream, the plumbing read lock is for the same Stream and
the validity of any
q_next
pointer within the Stream is guaranteed.
- (3)
- The Stream must be in a thawed state,
see
unfreezestr(9),
before any
qi_putp()
or
qi_srvp(9)
procedure will be entered within the Stream. However, the Stream may become frozen after (or
immediately before) the
qi_putp()
procedure is called.
(Freezing a Stream with
freezestr(9)
is advisory to threads entering
qi_putp(9)
or
qi_srvp()
procedures, and is mandatory for threads attempting to alter the state of the target queue.)
- (4)
- Queue put and service procedures will have been enabled with
qprocson(9)
for the queue pair containing the
qi_putp()
procedure before the call,
and will not be disabled with
qprocsoff(9)
for the queue pair until after the call.
- (5)
- If an
mp-streams(9)
synchronization specification has been made for the driver or module, the calling thread will enter
the inner synchronization barrier shared or exclusive (depending on the specification) before the
call to
qi_putp()
and will leave the barrier after its return.
In contrast to the
qi_srvp(9)
procedure, that handles deferred processing of messages,
the
qi_putp()
procedure is responsible for the immediate disposition of a message passed to the Stream end or from
a neighbouring queue.
qi_putp()
procedures are responsible for the disposition of the message reference,
mp,
and all references held by the caller of
put(9)
or
putnext(9)
are invalidated by the call.
There are three actions that a
qi_putp()
procedure can take with regard the disposition of the passed in message:
- (1)
- free the message (or part of the message) with a
STREAMS
utility such as
freeb(9)
or
freemsg(9);
- (2)
- pass the message (or part of the message) to another queue using
put(9)
or
putnext(9);
or,
- (3)
- place the message (or part of the message) on the queue's own message queue using a
STREAMS
utility such as
appq(9),
insq(9),
putq(9),
or
putbq(9).
The
qi_putp()
procedure is allowed to modify the passed in message at its discretion before applying one of the
above terminal dispositions to the message.
However, the
qi_putp()
procedure should not modify the contents of the data buffer associated with any data block,
datab(9),
that has a reference count,
db_ref,
greater than one
(1)
[see
dupmsg(9)].
Message blocks with a data block reference greater than one should be copied and the copy altered
instead.
Any other actions taken with regard to the message form part of the definition of the module or
driver concerned.
USAGE
The driver or module
qi_putp()
procedure is responsible for maintaining proper operations of the Stream by handling specific
message types in specific fashions.
The following sections provide some guidelines for the design of
qi_putp()
procedures from a driver or module, and rules for handling of messages within the procedure:
Driver and Module qi_putp() Design Rules
The following design rules apply to both drivers and modules:
- *
- Every queue must have a
qi_putp()
procedure defined in its associated
qinit(9)
structure, specified by the driver or module in its defining
streamtab(9)
structure.
- *
- Any
qi_putp()
procedure that places messages to its own queue using
appq(9),
insq(9),
putq(9),
putbq(9),
must also have a corresponding
qi_srvp(9)
procedure defined for the queue.
When no corresponding
qi_srvp(9)
procedure is defined, the
qi_putp(9)
procedure should not place messages on its own queue and must either free them or pass them along
using
putnext(9).
- *
- A
qi_putp()
procedure must not place messages directly on a neighbouring queue's message queue using the
putq(9)
or
putbq(9)
STREAMS
utilities.
It must only call
put(9)
or
putnext(9)
for the neighbouring queue to pass messages.
- *
- qi_putp()
procedures must not sleep or preempt.
Any
qi_put()
procedure must be congnisant of the fact that it can be called typically with local hardware or
software interrupts suppressed. This places two requirements on the procedure:
-
- 1)
- Message processing performed directly by the
qi_putp()
procedure must be brief.
Any long processing required on a message will be deferred to a
qi_srvp(9)
procedure by enqueueing the message on the message queue.
-
- Perfoming extensive message processing directly from a
qi_putp()
procedure, or causing a
qi_putp()
to sleep, can have a detrimental impact on
GNU/Linux
system performance and latency of response to time-critical events.
- 2)
- qi_putp()
procedure called at interrupt has a limited processor stack. Processing performed by a
qi_putp()
procedure should be performed directly out of the
qi_putp()
function, (i.e., without nesting too many subroutine calls), and must be congnisant of the fact that
the operational stack may be limited.
-
- Each call to
put(9)
or
putnext(9)
from within a
qi_putp()
procedure nests a direct function call to another
qi_putp()
procedure. If many function calls are nested while processing
qi_putp()
procedures along a Stream in this fashion, the kernel or interrupt stack could be overflowed.
Calls to
put(9)
or
putnext(9)
from a driver or module
qi_putp()
procedure should stack no local variables, and should be called within the same stack frame as the
qi_putp()
procedure.
-
- Overflowing an interrupt stack may cause the
GNU/Linux
system to panic or otherwise destabilize the kernel.
- *
- qi_putp()
procedures are not allowed to access (directly or indirectly via kernel utilities) the
current
user task structure.
The task that is
current
when a
qi_putp()
procedure is invoked can be any task in the
GNU/Linux
system, and has no fixed relationship to the user that invoked the chain of events resulting in
the procedure being called.
- *
- Every
qi_putp()
procedure is responsible for flow control within the Stream. Message handling rules for flow
control must be followed whenever messages are to be passed to a neighbouring queue. Flow control
rules are as follows:
-
- 1)
- Messages that are of high priority [see
datab(9)]
can be passed to a neighbouring queue without regard to flow control or message ordering within the
message queue.
- 2)
- A module that has no service procedure, may pass messages to a neighbouring queue without
regard to flow control. Modules that have no service procedure are designed a filtering modules
that do not normally generate or consume messages within a data stream.
- 3)
- Messages that are of normal priority (ordinary or priorty messages), must be maintained in sequence
with regard to other messages of the same priority on the message queue. That is, if a message of
the same priority already exists on the message queue, an arriving message must be queued in order
behind it. (The
STREAMS
putq(9)
utility maintains such ordering.)
- 4)
- For a read queue, normal priority messages should not be passed by a driver or module while the
message queue is empty and the
qi_srvp(9)
procedure is processing a message.
This is because a
qi_putp()
procedure on the read side can be invoked at hard or soft interrupt context, interrupting the
qi_srvp(9)
procedure processing that runs under process or
STREAMS
context.
This is necessary because the
qi_srvp(9)
procedure may very well place the message it is processing
back on the queue with
putbq(9)
disrupting message ordering.
-
- This is not normally the case on the write side, where the
qi_putp()
procedure is invoked in process or
STREAMS
context, and cannot normally interrupt a
qi_srvp(9)
procedure.
-
- Note that when the
qi_srvp(9)
procedure is running, the
QSVCBUSY
flag is set for the queue; and, when it is processing a message,
the
QWANTR
flag is clear for the queue.
-
- Otherwise, the
qi_srvp(9)
procedure can use an alternate mechanism to block the
qi_putp()
procedure from passing messages, or signal the
qi_putp()
procedure that it must queue messages (e.g., by taking basic locks, signalling via a shared
state module private data structure, or raising its software priority level to that of the
qi_putp()
procedure).
- 5)
- Messages that are of normal priority that are to be passed to a neighbouring queue, in accordance
with the above, must have flow control checked for the neighbouring queue using the
canput(9),
canputnext(9),
bcanput(9),
bcanputnext(9),
STREAMS
utilities.
When the called utility returns false, the message must not be passed, but may be enqueued to the
local message queue using
putq(9)
(or discarded).
Module qi_putp() Design Rules
The following design rules apply to modules:
- *
- If a module
qi_putp()
procedure is passed a message containing a message type that it does not recognize, it should pass
the message to the next module in the Stream (in accordance with queueing and flow control rules
appropriate to the priority of the message).
- *
- Modules must follow the module rules for handling specific message types. These rules are detailed
on the manual page describing the message type (e.g.,
M_FLUSH(9)).
For a list of message types and their corresponding manual pages, see
datab(9).
Driver qi_putp() Design Rules
The following design rules apply to drivers:
- *
- If a driver
qi_putp()
procedure is passed a message containing a message type that it does not recognize, it should
discard (ignore and free) the message.
- *
- Drivers must follow the driver rules for handling specific message types. These rules are detailed
on the manual page describing the message type (e.g.,
M_FLUSH(9)).
For a list of message types and their corresponding manual pages, see
datab(9).
ISR Design Rules
These design rules apply to device drivers (that process read events at interrupt).
The write side
qi_putp()
processing is similar to that of a module or pseudo-device driver with the additional consideration
that device actions can be performed from either the
qi_putp()
or
qi_srvp(9)
procedures.
The read side
qi_putp()
processing is normally different and is described in the points that follow:
- *
- Messages must be placed on the read side queue from an ISR or bottom-half using the
put(9)
utility and not the
putnext(9)
utility.
Linux Fast-STREAMS
defers
qi_putp()
processing when
put(9)
is invoked at hard interrupt. Messages are placed in a separate event queue to be processed later
by the
STREAMS
scheduler.
- *
- Whenever it is necessary to test flow control from an ISR, the read side queue usually requires a
qi_srvp(9)
procedure, and the
canput(9)
or
bcanput(9)
forms of the test should be used (and not the
canputnext(9)
or
bcanputnext(9)
forms of the test).
- *
- Designs that perform a
putnext(9)
from the driver read side
qi_putp()
procedure are difficult because the module above the driver might not have properly considered that
its read side
qi_putp()
procedure will be invoked at interrupt or bottom-half.
Designs that incorporate a read side
qi_srvp(9)
procedure work better even if the module above was so designed.
Calling
putnext(9)
in the
qi_putp()
procedure, however, may result in reduced processing latency.
- *
- ISRs and bottom-halves may call
putq(9)
to place a message on the read side message queue; however, it is considered better form to provide
a
qi_putp()
procedure, even if it simply calls (or is a function pointer to)
putq(9).
- *
- MP-safe drivers and ISRs may be difficult to design of they directly invoke functions used by the
driver's
qi_putp()
or
qi_srvp(9)
procedure. It is easier to place queue specialized messages (such as
M_CTL(9))
to the read side message queue with
put(9)
and let
mp-streams (9)
synchronization do the work.
This approach also works well for external asynchronous events (e.g., timeouts) is a psuedo-device
driver, or even in a module.
In general, any kernel subsystem outside of
STREAMS
that places messages on a Stream end should follow the same rules as those for ISRs and
bottom-halves described above.
RETURN
The
qi_putp()
procedure returns an integer value. This value is ignored by
STREAMS
and should always be zero
(0).
ERRORS
Although the
qi_putp()
procedure is capable of returning an error code, the returned value is always ignored by
STREAMS
and cannot be passed back to the caller of
put(9)
or
putnext(9),
because these functions return
void.
CONTEXT
A driver or module
qi_put()
procedure,
when invoked correctly,
can be called by
STREAMS
in any context, including process,
STREAMS,
software interrupt,
and
hard interrupt contexts.
There is no general portable way for a
qi_put()
procedure to determine the context in which it was called.
The non-portable
current_context(9)
utility can be used under
Linux Fast-STREAMS
to determine the current context.
MP-STREAMS
Synchronized Modules and Drivers
If
mp-streams(9)
synchronization has been specified for the driver or module, the inner synchronization barrier, if
any, is entered shared or exclusive in accordance with the synchronization specification for the
driver or module, across the call to the
qi_putp()
procedure. If synchronization has not been specified for the driver or module (that is, the module
or driver is specified as MP-safe), the
qi_putp()
procedure is invoked without synchronization.
MP-Safe Modules and Drivers
qi_putp()
is called by
STREAMS
in the context in which the
put(9)
or
putnext(9)
utility was invoked. Regardless of the context, when properly invoked,
STREAMS
is aware of which queue is being processed on a per-processor basis.
When invoked by
put(9),
STREAMS
acquires and holds a Stream head plumbing read lock, for the Stream within which the queue resides,
across the call to the
qi_putp()
procedure.
This permits the
qi_putp()
procedure, and any
STREAMS
utility functions called by the
qi_putp()
procedure, to dereference any
q_next
pointer in the Stream, and the dereference will remain valid for the duration of the
qi_putp()
call.
Note that this does not provide any assurances of the validity of a
q_next
pointer dereference in any other Stream, such as another Stream in an upper or lower multiplex: the
qi_putp()
procedure is responsible for asserting its own assurances in that regard.
(Note that freezing a Stream with
freezestr(9)
guarantees validity of all subsequent
q_next
pointer derefernces until the Stream is thawed with
unfreezestr(9)).
If the Stream containing the queue,
q,
has been frozen with a call to
freezestr(9),
by a processor,
STREAMS
running on another processor will not enter any
qi_putp()
procedure in the Stream, but will spin awaiting the thawing of the Stream by the processor that
froze it, with a call to
unfreezestr(9).
If the Stream was frozen after the
qi_putp()
procedure began execution, any attempt by the procedure to alter the state of the queue
targetted in the
freezestr(9)
command that froze the Stream, will spin until the Stream is thawed by
unfreezestr(9).
No
qi_putp()
procedure for a queue pair that has not yet had
qprocson(9)
called for the queue pair, or that has not returned from its
qi_qopen(9)
routine, will be executed by
STREAMS.
Once a
qi_putp()
is executing, any call to
qprocsoff(9)
for the queue pair will spin until the
put(9)
call exits and releases the Stream head plumbing read lock.
If
put(9)
has been called, but procedures are then turned off for the queue pair with
qprocsoff(9)
before the call has a chance to complete, when it is time to call the
qi_putp()
procedure,
put(9)
will effectively perform a
putnext(9)
if the queue belongs to a module, or
freemsg(9)
if the queue belongs to a driver.
For MP-Safe drivers and modules,
multiple threads can be executing the
qi_putp()
procedure concurrently for the same queue (but different messages).
Also, other threads may be executing the
qi_srvp(9),
qi_qopen(9),
q_qclose(9),
or
q_qadmin(9),
procedures and routines concurrently. It is the responsible of the writer of the
qi_putp()
procedure to acquire and hold the necessary locks to provide exclusive access to data structures
shared across these calls.
freezestr(9)
is inadequate in this case, and the procedures should use driver or module private locks.
NOTICES
A queue
qi_putp()
procedure is an internal
STREAMS
entry point to the driver or module, that is not intended to be called directly by the module or
driver writer. See
put(9)
and
putnext(9)
for accepted methods of invoking this procedure.
STYLE
It is common practise to name
qi_putp()
procedures as follows, (where
prefix
is the configuration prefix chosen for the driver or module and typically derived from the name of
the driver or module, and which may contain a trailing underscore):
- prefixrput()
- read side of a module or upper multiplex read side of a driver;
- prefixwput()
- write side of a module or upper multiplex write side of a driver;
- prefixmuxrput()
- lower multiplex read side of a driver; and,
- prefixmuxwput()
- lower multiplex write side of a driver.
EXAMPLES
Example #1 - Module qi_putp()
The following example of a module
qi_putp()
procedure comes directly from the write side of the
bufmod(4)
module located in
src/modules/bufmod.c
source file in the
streams-0.9.2.4
distribution:
1 static int
2 bufmod_wput(queue_t *q, mblk_t *mp)
3 {
4 if (unlikely(mp->b_datap->db_type == M_FLUSH)) {
5 if (mp->b_rptr[0] & FLUSHW) {
6 if (mp->b_rptr[0] & FLUSHBAND)
7 flushband(q, FLUSHALL, mp->b_rptr[1]);
8 else
9 flushq(q, FLUSHALL);
10 }
11 }
12 if (likely(mp->b_datap->db_type >= QPCTL
13 || (q->q_first == NULL
14 && !(q->q_flag & QSVCBUSY)
15 && bcanputnext(q, mp->b_band)))) {
16 putnext(q, mp);
17 return (0);
18 }
19 /* always buffer, always schedule out of service
20 procedure for testing */
21 if (unlikely(putq(q, mp) == 0)) {
22 mp->b_band = 0;
23 putq(q, mp); /* this must succeed */
24 }
25 return (0);
26 }
The operation of the
bufmod(4)
module is described in the
bufmod(4)
manual page.
The write
qi_putp()
procedure passes all messages downstream and performs flow control and buffering.
- Line 4-11:
- The module performs processing of the
M_FLUSH(9)
message for modules as described in the
M_FLUSH(9)
manual page.
- Line 12-18:
- If the the message is a high priority message it is passed to the next driver or module using
putnext(9)
without consideration for flow control.
If the message is a normal priority message, the message queue is empty, the service procedure
is not running, and the message band is not flow controlled forward, the message is also passed to
the next driver or module using
putnext(9).
- Line 21-24:
- In all other situations (the message is a normal priority message, the queue is not empty or the
service procedure is running or the message band is flow controlled forward), the message is placed
on the message queue to be processed by the service procedure.
- Line 17,25:
- The module put procedure always returns zero.
See the
src/modules
directory in the
streams-0.9.2.4
distribution for more working examples of module put procedures.
Example #2 - Driver qi_putp()
The following example of a driver
qi_putp()
procedure comes directly from the lower read side of the
mux(4)
multiplexing driver located in
src/modules/mux
source file in the
streams-0.9.2.4
distribution:
1 static int
2 mux_muxrput(queue_t *q, mblk_t *mp)
3 {
4 struct mux *mux = q->q_ptr;
5
6 switch (mp->b_datap->db_type) {
7 case M_FLUSH:
8 {
9 if (mp->b_rptr[0] & FLUSHR) {
10 if (mp->b_rptr[0] & FLUSHBAND)
11 flushband(q, mp->b_rptr[1], FLUSHALL);
12 else
13 flushq(q, FLUSHALL);
14 }
15
16 read_lock(&mux_lock);
17 if (mux->other) {
18 queue_t *rq;
19
20 if ((rq = mux->other->rq)) {
21 putnext(rq, mp);
22 read_unlock(&mux_lock);
23 return (0);
24 }
25 }
26 read_unlock(&mux_lock);
27
28 if (!(mp->b_flag & MSGNOLOOP)) {
29 if (mp->b_rptr[0] & FLUSHW) {
30 if (mp->b_rptr[0] & FLUSHBAND)
31 flushband(WR(q), mp->b_rptr[1],
32 FLUSHALL);
33 else
34 flushq(WR(q), FLUSHALL);
35 mp->b_rptr[0] &= ~FLUSHR;
36 /* pretend to be STREAM head */
37 mp->b_flag |= MSGNOLOOP;
38 qreply(q, mp);
39 return (0);
40 }
41 }
42 freemsg(mp);
43 break;
44 }
45 default:
46 if (!q->q_first && !(q->q_flag & QSVCBUSY)) {
47 read_lock(&mux_lock);
48 if (mux->other) {
49 queue_t *rq;
50
51 if ((rq = mux->other->rq)
52 && (mp->b_datap->db_type >= QPCTL
53 || bcanputnext(rq, mp->b_band))) {
54 putnext(rq, mp);
55 read_unlock(&mux_lock);
56 return (0);
57 }
58 }
59 read_unlock(&mux_lock);
60 }
61 putq(q, mp);
62 break;
63 }
64 return (0);
65 }
The operation of the
mux(4)
multiplexing driver is described in the
mux(4)
manual page.
- Line 7-44:
- The driver performs
M_FLUSH(9)
processing according to the rules for drivers as described in the
M_FLUSH(9)
manual page, with one wrinkle: flushing across the multiplexing driver is supported.
- Line 45-63:
- The driver processes all other messages by passing them across the multiplexing driver or queueing
them on the message queue.
- Line 46:
- If the message queue is not empty or the service procedure is running, messages are queued to the
message queue to preserve order.
- Line 47,59:
- A read lock is taken to protect the driver private (which is changed by ioctl operations on the
upper side of the driver).
- Line 51-57:
- If there is no path to the upper multiplex, messages are simply queued to the message queue awaiting
assignment of an upper multiplex path. If there is a path and the message is a high priority
message, it is passed without flow control consideration; a normal priority message is only passed
if the message band is not flow controlled at the upper multiplex. Otherwise, messages are simply
queued to the messge queue.
See the
src/drivers
directory in the
streams-0.9.2.4
distribution for more working examples of driver put procedures.
SEE ALSO
queue(9),
msgb(9),
datab(9),
qi_qopen(9),
qi_qclose(9),
qi_qadmin(9),
qi_srvp(9),
qinit(9),
streamtab(9),
put(9),
putnext(9),
freezestr(9),
unfreezestr(9),
qprocson(9),
qprocsoff(9),
mp-streams(9),
freeb(9),
freemsg(9),
appq(9),
insq(9),
putq(9),
putbq(9),
dupmsg(9),
canput(9),
canputnext(9),
bcanput(9),
bcanputnext(9),
M_FLUSH(9),
M_CTL(9),
current_context(9),
bufmod(4),
mux(4),
STREAMS(9).
BUGS
Linux Fast-STREAMS
invocation of the
qi_putp()
entry point has no known bugs.
COMPATIBILITY
The
qi_putp()
procedure is compatible with
SVR 4.2[1]
and implementations based on
SVR 4[2],
with the following portability considerations:
- ---
- SVR 4.2[3]
did not define a type for the prototype of a queue
qi_putp(9)
procedure. This was an embellishment that first appeared in
OSF/1® 1.1[4],
and propagated to
AIX®[5]
and
HP-UX®[6].
-
- Portable
STREAMS
drivers and modules will not directly reference the
qi_putp_t
type.
- ---
- Solaris®[7]
always defers calling the
qi_putp()
procedure when
put(9)
or
putnext(9)
is called to avoid overflowing the kernel stack.
Linux Fast-STREAMS
only defers when
put(9)
is called from hard interrupt context.
-
- Portable
STREAMS
drivers will not be designed so as to expect a
qi_putp()
procedure to be invoked as a direct function call nested within a
put(9)
or
putnext(9)
call.
- ---
- Some implementations permit a wider range of
STREAMS
utilities to be called from outside of
STREAMS.
HP-UX®[6]
limits the set in a similar manner to
Linux Fast-STREAMS,
however,
Linux Fast-STREAMS
permits the larger set to be used in some circumstances.
-
- Portable
STREAMS
drivers will restrict the use of
STREAMS
utilities called from outside the
STREAMS
environment to
put(9),
canput(9),
and
bcanput(9),
and the later two will only be used if the target driver queue has a service procedure.
- ---
- The same applies to placing messages on Stream ends across a multiplexing driver.
-
- Portable
STREAMS
drivers will restrict the
STREAMS
utilities used to operate on a different Stream to
put(9),
canput(9),
and
bcanput(9).
Again, the later two will only be used if the target driver queue has a service procedure.
- ---
- Some
STREAMS
implementations do not permit
putnext(9)
to be called at hard interrupt.
Linux Fast-STREAMS
permits
putnext(9)
to be called at hard interrupt.
-
- Portable
STREAMS
drivers will not call
putnext(9)
from a driver read
qi_putp()
procedure, but, rather, will call
putq(9)
to queue the message to the message queue and call
putnext(9)
from the
qi_srvp(9)
procedure when it runs.
- ---
- Because a number of the primary data structure and types have different definitions on the
GNU/Linux
system, binary compatibility is not guaranteed.
See
STREAMS(9)
for additional compatibility considerations.
CONFORMANCE
SVR 4.2 MP[3].
HISTORY
The
qi_putp_t
type first appeared in
OSF/1® 1.1[4].
The queue put procedure first appeared in
SVR 3[8].
REFERENCES
- [1]
- USL DDI/DKI,
Device Driver Interface/Driver-Kernel Interface (DDI/DKI) Reference Manual for Intel Processors, 1992, (Englewood Cliffs, New Jersey), AT&T UNIX System Laboratories, Inc., Prentice Hall.
- [2]
- SVR 4,
UNIX® System V Release 4 STREAMS Programmer's Guide, 1990, (Englewood Cliffs, New Jersey), AT&T UNIX System Laboratories, Inc., Prentice Hall.
- [3]
- SVR 4.2,
STREAMS Programmer's Guide, 1992, (Englewood Cliffs, New Jersey), AT&T UNIX System Laboratories, Inc., Prentice Hall.
- [4]
- Digital® UNIX (OSF/1.2),
Digital UNIX: Network Programmers Guide, 1996, (Palo Alto, California), Digital Equipment Corporation, Hewlett-Packard Company.
<http://www.true64unix.compaq.com/docs/>
- [5]
- AIX® 5L Version 5.1,
AIX STREAMS Programmers Guide, 2001, (Boulder, Colorado), Internatonal Business Machines Corp., IBM.
<http://publibn.boulder.ibm.com/>
- [6]
- HP-UX STREAMS,
STREAMS Programmer's Guide -- HP 9000 and Integrity Server Computer Systems, October 2005, (Palo Alto, California), Hewlett-Packard Development Company L.P., HP.
<http://docs.hp.com/>
- [7]
- Solaris® 8,
STREAMS Programming Guide, August 1999, (Palo Alto, California), Sun Microsystems, Inc., Sun.
[Part No: 805-7478-05]
<http://docs-pdf.sun.com/>
- [8]
- SVR 3,
UNIX® System V Release 3 Programmer's Manual, (Englewood Cliffs, New Jersey), AT&T UNIX System Laboratories, Inc., Prentice Hall.
TRADEMARKS
- OpenSS7tm
- is a trademark of OpenSS7 Corporation.
- Linux®
- is a registered trademark of Linus Torvalds.
- UNIX®
- is a registered trademark of The Open Group.
- Solaris®
- is a registered trademark of Sun Microsystems.
Other trademarks are the property of their respective owners.
IDENTIFICATION
-
Linux Fast-STREAMS: Package streams version 0.9.2.4 released 2008-10-31.
Copyright©1997-2008OpenSS7 Corp.
All Rights Reserved.
(See roff source for permission notice.)
Index
- NAME
- SYNOPSIS
- ARGUMENTS
- INTERFACE
- DESCRIPTION
- USAGE
- Driver and Module qi_putp() Design Rules
- Module qi_putp() Design Rules
- Driver qi_putp() Design Rules
- ISR Design Rules
- RETURN
- ERRORS
- CONTEXT
- MP-STREAMS
- Synchronized Modules and Drivers
- MP-Safe Modules and Drivers
- NOTICES
- STYLE
- EXAMPLES
- Example #1 - Module qi_putp()
- Example #2 - Driver qi_putp()
- SEE ALSO
- BUGS
- COMPATIBILITY
- CONFORMANCE
- HISTORY
- REFERENCES
- TRADEMARKS
- IDENTIFICATION
This document was created by
man2html,
using the manual pages.
Time: 22:33:59 GMT, May 18, 2013