pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)NAME
pfMultipipe, pfGetMultipipe, pfMultithread, pfGetMultithread,
pfMultiprocess, pfGetMultiprocess, pfMultithreadParami,
pfGetMultithreadParami, pfMultithreadParamf, pfGetMultithreadParamf,
pfMultithreadParam, pfGetMultithreadParam, pfGetMPBitmask, pfConfig,
pfIsConfiged, pfGetPID, pfGetPIDName, pfCreateProcessFunc,
pfGetCreateProcessFunc, pfProcessMiscCPU, pfGetProcessMiscCPU,
pfPrintProcessState, pfGetPipe, pfInitPipe, pfGetStage, pfGetStageName,
pfStageConfigFunc, pfGetStageConfigFunc, pfConfigStage, pfHyperpipe,
pfGetHyperpipe, pfGetPipeHyperId, pfProcessPriorityUpgrade,
pfGetProcessPriorityUpgrade, pfProcessHighestPriority,
pfGetProcessHighestPriority - Configure process and pipeline models, get
pfPipe handle and process ID.
FUNCTION SPECIFICATION
#include <Performer/pf.h>
int pfMultipipe(int num);
int pfGetMultipipe(void);
int pfMultithread(int pipe, uint stage,
int nprocs);
int pfGetMultithread(int pipe, uint stage);
int pfMultiprocess(int mode);
int pfGetMultiprocess(void);
int pfMultithreadParami(int pipe, int param,
unsigned int value);
int pfGetMultithreadParami(int pipe, int param);
int pfMultithreadParamf(int pipe, int param,
float value);
float pfGetMultithreadParamf(int pipe, int param);
int pfMultithreadParam(int pipe, int param,
void *value);
void * pfGetMultithreadParam(int pipe, int param);
int pfGetMPBitmask(void);
int pfConfig(void);
int pfIsConfiged(void);
Page 1
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
pid_t pfGetPID(int pipe, uint stage);
const char * pfGetPIDName(pid_t pid);
void -
pfCreateProcessFunc(pfCreateProcessFuncType func);
pfCreateProcessFuncType pfGetCreateProcessFunc(void);
void pfProcessMiscCPU(int cpu);
int pfGetProcessMiscCPU(void);
void pfPrintProcessState(FILE *fp);
pfPipe * pfGetPipe(int pipe);
int pfInitPipe(pfPipe *pipe,
pfPipeFuncType configFunc);
uint pfGetStage(pid_t pid, int *pipe);
const char * pfGetStageName(int pipe, uint stage);
void pfStageConfigFunc(int pipe, uint stageMask,
pfStageFuncType configFunc);
pfStageFuncType pfGetStageConfigFunc(int pipe, uint stageMask);
void pfConfigStage(int pipe, uint stageMask);
void pfHyperpipe(int n);
int pfGetHyperpipe(pfPipe *pipe);
int pfGetPipeHyperId(const pfPipe *pipe);
void pfProcessPriorityUpgrade(int state);
int pfGetProcessPriorityUpgrade();
void pfProcessHighestPriority(int pri);
int pfGetProcessHighestPriority();
typedef void (*pfCreateProcessFuncType)(int _pipe, uint _stage, pid_t _pid);
typedef void (*pfStageFuncType)(int pipe, uint stage);
typedef pfGeoSet *(*pfSidekickFunc)(pfGeoSet *gset, pfDispListOptimizer *op, void *userData);
Page 2
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)DESCRIPTION
An OpenGL Performer application renders images using one or more pfPipes.
A pfPipe is a software rendering pipeline that traverses, culls, and
draws one or more pfChannels into a single graphics context. The software
rendering pipeline is composed of three functional stages:
APP Application processing
CULL Database culling and level-of-detail selection
DRAW Drawing geometry produced by CULL
In addition, OpenGL Performer has a separate intersection stage which can
operate either synchronously or asynchronously with the rendering
pipeline (see pfIsectFunc).
All stages may be combined into a single process or split into multiple
processes for enhanced performance on multiprocessing systems.
pfMultiprocess controls the partitioning of functional stages into
processes. mode is a bitwise OR of the following tokens:
PFMP_FORK_ISECT
PFMP_FORK_CULL
PFMP_FORK_DRAW
PFMP_FORK_LPOINT
PFMP_FORK_DBASE
PFMP_FORK_COMPUTE
PFMP_FORK_CULL_SIDEKICK
PFMP_CULLoDRAW
PFMP_CULL_DL_DRAW
These tokens specify which stages to fork into separate processes and
what multiprocessing communication mechanism to use between the cull and
draw processes.
The process from which all other processes are spawned is known as the
application process, or APP. This process is the one that invokes
pfConfig and controls the rendering and intersection pipelines through
pfFrame.
User code in the intersection, database, cull, and draw processes are
"triggered" by calling pfFrame. pfFrame causes OpenGL Performer to invoke
the user callbacks associated with each process. These callbacks are
established by pfIsectFunc, pfDBaseFunc, pfChanTravFunc respectively. See
pfFrame for more details.
In addition to the cull and draw process, an optional light points
process can be used to discharged the draw process to do the intensive
computation involved by the pfLPointState attached to the lights points
pfGeoSet. This process is usefull when a lot of raster computation can
be done on a separate processor than the draw processor, and will become
Page 3
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
mandatory when using the forthcoming calligraphic light points.
The cull process will put all geoset with a pfLPointState attached to in
a dedicated bin. The light points process will preprocess this bin in
parallel with the draw process drawing the other bins. The light points
process uses an internal ring display list to communicate the result of
the preprocessing to the draw, which will therefore draw all light points
at the end. See pfChannel for more details.
Each pfPipe has a CULL and DRAW stage which may be configured as either
one or two processes. The ISECT, DBASE, and COMPUTE stages are
independent of any pfPipe and may run in the same process as the
application process or as separate processes (PFMP_FORK_ISECT,
PFMP_FORK_DBASE, PFMP_FORK_COMPUTE). In the latter case, the user may
further multiprocess intersection traversals through any IRIX
multiprocessing mechanism such as fork, sproc, or m_fork. Database
processing utilizing the pfBuffer mechanism may be further parallelized
through fork only (See pfBuffer).
For additional performance gains when a pfPipe contains multiple
pfChannels, the CULL stage may be further parallelized on a per-pfChannel
basis. When the stage argument to pfMultithread is PFPROC_CULL, the CULL
stage of the pipeth rendering pipeline is split into nprocs forked
processes each of which operates singly on a pfChannel. Thus this extra
parallelization is only effective when both nprocs and the number of
pfChannels on pipe are greater than 1. nprocs need not be equal to the
number of pfChannels. Currently, pfMultithread only accepts a stage
argument of PFPROC_CULL, returns 1 on success and -1 otherwise. The CULL
is not automatically multithreaded if PFMP_DEFAULT is specified as the
pfMultiprocess mode.
The LPOINT stage can also be multithreaded, using the same scheme as for
the cull process.
When multithreading the CULL, care must be taken to avoid data collisions
in user callback functions. In particular, pfChannel and pfNode CULL
callbacks (pfChanTravFunc, pfNodeTravFuncs) may be invoked in parallel.
A set of helper processes named CULL_SIDEKICK may be added alongside the
CULL process. These helper processes traverse the display list that the
CULL process produces. They perform optimizations on each pfGeoSet on the
display list. You can only add CULL_SIDEKICK processes when both CULL
and DRAW are forked. Each CULL process may have one or more CULL_SIDEKICK
processes serving it. CULL_SIDEKICK processes don't add latency to the
rendering pipeline. They run at the same frame number as their master
CULL process. They wait for CULL to add pfGeoSets to the display list and
process them as they appear. CULL_SIDEKICKs may not finish processing all
the pfGeoSets on a display list. Their job is to remove unnecessary
geometry from the display list. Any removed geometry helps the DRAW
process draw less geometry and achieve better frame rates.
Use pfMultithread in order to specify the number of CULL_SIDEKICKs for
Page 4
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
each CULL process. Use PFPROC_CULL_SIDEKICK as the stage parameter. Use
the rest of the parameters as in CULL threads. You can control the
behavior of CULL_SIDEKICK processes using the functions
pfMultithreadParamf and pfMultithreadParami.
pfMultithreadParami sets integer parameters to the CULL_SIDEKICK
processes. pipe is pipe number of the master CULL process. param can be
any of the following:
PFSK_POLICY
Sets the synchronization policy between a CULL process and its
CULL_SIDEKICK helpers.
PFSK_CULL_DONE makes CULL_SIDEKICKs finish their frame as soon
as their master CULL process finishes its frame. In this mode,
CULL_SIDEKICKs don't always complete processing all the display
list that their CULL master generated.
PFSK_CULL_FRAME_DONE makes CULL_SIDEKICKs use all the available
time specified by pfFrameRate. CULL_SIDEKICKs stop processing
within some safety margin before the end of the frame. This
safety margin can be specified by pfMultithreadParamf. The
default value is 1 millisecond.
PFSK_SIDEKICK_DONE makes CULL_SIDEKICKs complete processing the
CULL display list completely. In this mode, the CULL process
may slow down while waiting for CULL_SIDEKICKs to complete and
the application may miss frames.
The default policy is PFSK_CULL_DONE.
PFSK_OPTIMIZATION
Set the type of per-pfGeoSet optimization that the
CULL_SIDEKICK traversal performer. value should a bitwise OR of
the masks: PFSK_BACKFACE_CULL and PFSK_FRUSTUM_CULL.
PFSK_BACKFACE_CULL makes CULL_SIDEKICKs test each of the
polygons in a pfGeoSet and remove backfacing ones.
PFSK_FRUSTUM_CULL makes CULL_SIDEKICKs frustum-test each of the
polygons in a pfGeoSet and remove invisible ones. The default
optimization mask is (PFSK_FRUSTUM_CULL|PFSK_BACKFACE_CULL).
pfMultithreadParami sets floating point parameters to the CULL_SIDEKICK
processes. pipe defines the pipe number for the master CULL process.
param can be any of the following:
PFSK_SAFETY_MARGIN Sets a floating number of milliseconds. When a
CULL_SIDEKICKs runs with PFSK_POLICY == PFSK_CULL_FRAME_DONE,
you can set a margin before the end of the frame where
CULL_SIDEKICK stop processing. This is a safety measure. If
Page 5
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
CULL_SIDEKICK doesn't complete early enough, it can make CULL
miss its frame. The default value is 1.0 millisecond.
pfMultithreadParam sets void* parameters to the CULL_SIDEKICK processes.
pipe defines the pipe number for the master CULL process. param can be
any of the following:
PFSK_USER_FUNC Sets a user function for the CULL_SIDEKICK process.
The CULL_SIDEKICK process invokes this function for every
pfGeoSet it encounters. A user function should be of type
pfSidekickFunc. For more information about this option, see
man pfDispListOptimizer.
PFSK_USER_FUNC_DATA Sets user-data for the function specified by
the PFSK_USER_FUNC parameter above.
pfGetMultithreadParamf returns the values specified by
pfMultithreadParamf. pfGetMultithreadParami returns the values specified
by pfMultithreadParami. pfGetMultithreadParam returns the values
specified by pfMultithreadParam.
pfGetMultithread returns the number of processes in the processing stage
identified by stage on the pipeth rendering pipeline. Currently,
pfGetMultithread only accepts a stage argument of PFPROC_CULL,
PFPROC_CULL_SIDEKICK or PFPROC_LPOINT and returns -1 otherwise.
Thus, the number of processes an application uses is dependent on:
1. The multiprocessing modes set by pfMultiprocess and
pfMultithread.
2. The number of rendering pipelines set by pfMultipipe.
3. The number of user-spawned processes.
The following table indicates the number of processes that are implied by
each multiprocessing mode combination as a function of the number of
OpenGL Performer pfPipes specified.
FORK_ISECT FORK_CULL FORK_DRAW # Processes
___________________________________________________
No No No 1
No No Yes 2
No Yes No 1 + numPipes
No Yes Yes 1 + 2*numPipes
___________________________________________________
Yes No No 2
Yes No Yes 3
|
|
|
Page 6
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
Yes Yes No 2 + numPipes
Yes Yes Yes 2 + 2*numPipes
|
|
|
Here is an example configuration which would be used to generate a high-
performance stereo display using two pfPipes, each associated with a
hardware graphics pipeline. In this situation the output of one pipeline
will be displayed for the viewer's left eye, and the other will go to the
right eye. Here, multithreading the CULL is of no use since each
pfChannel is handled by its own pfPipe.
Example 1: Two pfPipe stereo configuration
/* configure two hardware pipelines */
pfMultipipe(2);
/* operate processing tasks in parallel */
pfMultiprocess(PFMP_FORK_CULL | PFMP_FORK_DRAW | PFMP_FORK_ISECT);
The processing mode configured by this example looks like:
CULL ---> DRAW left eye
/
/
APP
/ \
/ \
ISECT CULL ---> DRAW right eye
Example 2: One pfPipe stereo configuration using multithreaded CULL
/* operate all processing tasks in parallel */
pfMultiprocess(PFMP_FORK_CULL | PFMP_FORK_DRAW | PFMP_FORK_ISECT);
pfMultithread(0, PFPROC_CULL, 2);
The processing mode configured by this example looks like:
CULL left eye
/ \
APP----- ---------> DRAW
/ \ /
/ CULL right eye
ISECT
Page 7
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
PFMP_CULL_DL_DRAW and PFMP_CULLoDRAW specify how the cull and draw stages
should communicate.
If PFMP_CULL_DL_DRAW is set the cull stage will build up an OpenGL
Performer display list (pfDispList) which contains the entire frame's
worth of data. The draw stage then traverses this pfDispList when pfDraw
is called and sends commands to the graphics hardware. When the cull and
draw stages are different processes (PFMP_FORK_DRAW) this mode is always
enabled. However, when the cull and draw stages are the same process, the
display list construction may add some overhead. If, in this case,
PFMP_CULL_DL_DRAW is not specified, the cull stage will be delayed until
pfDraw is called. pfDraw will then cull and draw the scene in immediate
mode and not use a pfDispList.
PFMP_CULL_DL_DRAW is disabled by default but should be used for
applications which use multipass rendering techniques that require
multiple calls to pfDraw.
The 'o' in PFMP_CULLoDRAW is short for 'overlap' and when this bit is
set, the multiprocessed cull and draw stages of the same frame will be
overlapped. The cull process (the producer) writes to a FIFO
(implemented as a ring buffer) while the draw process (the consumer)
simultaneously reads commands from the ring buffer.
The main benefit of this configuration is that latency will be reduced a
full frame time over the pipelined (non-overlapped) case. A disadvantage
is that the draw process may suffer from reduced throughput if the cull
process cannot keep up. This condition is exacerbated when the cull sorts
the database by draw bin or by graphics state. In each case, the cull
retains the database in internal data structures and does not add drawing
commands to the display list until the cull is completed. Consequently,
to get the best throughput from PFMP_CULLoDRAW, database mode sorting and
ordering should be disabled.
Example 3: Reasonable sorting setup for PFMP_CULLoDRAW
pfMultiprocess(PFMP_APP_CULL_DRAW | PFMP_CULLoDRAW);
/* Draw opaque geometry immediately into CULLoDRAW's pfDispList
* Transparent geometry is still saved and drawn after opaque. */
pfChanBinOrder(chan, PFSORT_OPAQUE_BIN, PFSORT_NO_ORDER);
/* PFCULL_SORT must be enabled for transparent geometry to be
ordered, i.e. - drawn last. */
pfChanTravMode(chan, PFTRAV_CULL, PFCULL_ALL);
PFMP_CULLoDRAW is ignored if the cull and draw stages are in the same
process.
Page 8
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
The optional light points process uses the Display List mechanism as an
essential way of communication between the cull and the draw. Therefore,
it is compulsory to use PFMP_CULL_DL_DRAW with PFMP_FORK_LPOINT.
pfConfig will automatically replace PFMP_CULLoDRAW token if used in
conjunction with light points process.
For convenience, other tokens are provided for common multiprocessing
modes:
PFMP_APPCULLDRAW
All stages are combined into a single process. A pfDispList is
not used. pfDraw both culls and renders the scene.
PFMP_APPCULL_DL_DRAW
All stages are combined into a single process. A pfDispList is
built by pfCull and rendered by pfDraw.
PFMP_APP_CULLDRAW
The cull and draw stages are combined in a process that is
separate from the application process. A pfDispList is not
used. pfDraw both culls and renders the scene. Equivalent to
(PFMP_FORK_CULL).
PFMP_APP_CULL_DL_DRAW
The cull and draw stages are combined in a process that is
separate from the application process. A pfDispList is built by
pfCull and rendered by pfDraw. Equivalent to (PFMP_FORK_CULL |
PFMP_CULL_DL_DRAW).
PFMP_APPCULL_DRAW
The application and cull stages are combined in a process that
is separate from the draw process. Equivalent to (-
PFMP_FORK_DRAW).
PFMP_APPCULLoDRAW
The application and cull stages are combined in a process that
is separate from, but overlaps, the draw process. Equivalent
to (PFMP_FORK_DRAW | PFMP_CULLoDRAW).
PFMP_APP_CULL_DRAW
The application, cull, and draw stages are each separate
processes. Equivalent to (PFMP_FORK_CULL | PFMP_FORK_DRAW).
PFMP_APP_CULLoDRAW
The application, cull, and draw stages are each separate
processes and the cull and draw process are overlapped.
Equivalent to (PFMP_FORK_CULL | PFMP_FORK_DRAW |
PFMP_CULLoDRAW).
PFMP_DEFAULT
OpenGL Performer will choose a multiprocessing mode based on
the number of pipelines required and the number of unrestricted
Page 9
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
processors available. This is also the default mode if
pfMultiprocess is not called. PFMP_DEFAULT will attempt to use
as many available processors as possible except the CULL will
not be automatically multithreaded.
Example 4: Configuration with a light point process
/* operate all processing tasks in parallel */
pfMultiprocess(PFMP_APP_CULL_DRAW | PFMP_FORK_LPOINT | PFMP_CULL_DL_DRAW);
The processing mode configured by this example looks like:
APP----- CULL ------->[ DRAW ..] (draws light points at the end)
/ /
/ -----> LPOINT / (preprocess light points in parallel to draw)
ISECT
By default OpenGL Performer uses a single pfPipe. If multiple rendering
pipelines are required (in most cases this will be for machines with
multiple hardware pipelines), use pfMultipipe to specify the number of
pfPipes that are created by pfConfig. Multipipe operation absolutely
requires that all participating hardware pipelines be genlocked.
Otherwise reduced throughput and increased latency will result.
The multiprocessing mode set by pfMultiprocess is used for all rendering
pipelines. However, OpenGL Performer never multi-threads the application
process although the application may choose to do so. If the application
itself multiprocesses, all OpenGL Performer calls must be made from the
process which calls pfConfig or results are undefined. When using
multiple pipelines, the cull stage must be forked (PFMP_FORK_CULL). If
not, OpenGL Performer defaults to PFMP_APP_CULL_DRAW.
pfMultiprocess, pfMultithread, and pfMultipipe must be called after
pfInit but before pfConfig. pfConfig configures OpenGL Performer
according to the required number of pipelines and multiprocessing modes,
forks the appropriate number of OpenGL Performer processes and returns
control to the single-threaded application. pfConfig should be called
only once between pfInit and pfExit. pfConfig returns a value of 1 if
successful and -1 if an error is detected.
pfIsConfiged returns a value of 1 if pfConfig has been successfully
called and a value of 0 otherwise.
OpenGL Performer uses fork to split off processes and will create the
Page 10
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
specified number of separate processes only when pfConfig is called.
Forked processes do not share the same address space as sproc'ed
processes so the application must establish shared memory communication
mechanisms between processes or use the shared memory features provided
by OpenGL Performer (see pfPassChanData, pfMalloc, pfGetSharedArena,
pfDataPool).
In particular, care must be taken when the DBASE stage is configured as a
separate process. Although deletion requests (pfDelete) may be made in
any process, DBASE frees all the memory so if DBASE is forked it can only
free memory that was allocated out of OpenGL Performer's shared memory
arena (pfGetSharedArena) or from some other memory arena that is visible
to the DBASE process. Consequently it is safest to allocate all objects
from a shared memory arena when using a forked DBASE process.
In addition to forking processes, pfConfig initializes the number of
pfFluxBuffer and pfCycleBuffer copies (pfFluxDefaultNumBuffers and
pfCBufferConfig) appropriate for the multiprocessing mode.
pfCreateProcessFunc allows the specification of a callback function that
is called when Performer creates any process (the pfConfig forked
processes, the pfClock process, and the sproced processes for managing
pfQueues). Users may specify a master process manager with this
mechanism for placing processes on CPUs and assigning them priorities. A
sample such process manager is in libpfutil and is set up with
pfuInitDefaultProcessManager and is the process manager used by perfly.
By default the pfClock and pfQueue processes are placed on the
miscellaneous CPU that defaults to CPU 0 and no other management is done
for the other created processes. pfGetCreateProcessFunc will return the
pointer to the current process manager function which will be the
internal default function if one has not been set by the user. pfMiscCPU
will set the miscellaneous CPU and pfGetMiscCPU will return the current
pfMiscCPU that defaults to CPU 0 if it has not been set.
After pfConfig is called, pfGetPipe should be used to get handles to
pfPipes for subsequent use in OpenGL Performer routines. pipe identifies
a pipe and ranges from 0 to numPipes - 1 where numPipes is the number of
pipes specified in pfMultipipe.
After pfConfig spawns other processes, pfGetPID will return the process
id of a specific pipeline stage or -1 to indicate error. pipe specifies
which pipeline the stage is in and ranges from 0 to numPipes - 1. stage
is a bitmask which identifies one or more stages in the multiprocessing
pipeline and may consist of:
Token Stage Description
__________________________________________________________________
PFPROC_ISECT The intersection stage
PFPROC_DBASE The database stage
PFPROC_COMPUTE The pfASD, pfEngine/pfFlux and user compute stage
|
Page 11
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
PFPROC_APP The application stage
PFPROC_CULL The cull stage
PFPROC_DRAW The draw stage
PFPROC_LPOINT The light points stage
PFPROC_CLOCK The clock process
|
If stage identifies multiple stages, such as (PFPROC_CULL | PFPROC_DRAW),
then the process id will be returned only if an exact match is made which
in this example is only possible if the multiprocessing mode is
PFMP_APP_CULLDRAW. Otherwise a -1 is returned.
pipe is ignored if stage identifies the PFPROC_ISECT, PFPROC_DBASE, or
PFPROC_APP stages since these stages are not associated with any OpenGL
Performer pipe.
pfGetStage is the "inverse" of pfGetPID. Given a process id, pid,
pfGetStage will return a bitmask which identifies the stages that are
performed by process pid and will copy into pipe the number of the
pipeline that pid is in if pipe is not NULL. pfGetStage returns -1 if pid
is not a known OpenGL Performer process.
The stage bitmask used in pfGetPID and pfGetStage identifies the thread
number (pfMultithread) as well as the processing stage(s). The thread ID
is OR'ed into the upper bits of the stage bitmask as follows:
threadId = (stage & PFPROC_THREAD_MASK) >> PFPROC_THREAD_SHIFT;
The PFPROC_THREAD1-7 tokens are provided as a convenience (more than 8
threads are supported).
pfGetPIDName takes a process id pid and will return a pointer to a string
with a description of the processing that includes stage, pid, and pipe.
pfGetStageName takes a pfPipe number pipeand stage bit stage and will
return the string pointer with the full discription of the corresponding
process.
pfPrintProcessState will print to the opened file specified by fp the
current list of Performer processes and their descriptions. If the file
pointer fp is NULL, the information will be printed using standard
pfNotify.
pfGetMultiprocess returns the requested multiprocess mode.
pfGetMPBitmask returns the actual multiprocess mode bitmask in use which
might be different than the requested mode if PFMP_DEFAULT was the
requested mode or if single process was requested with multipipe
operation. pfGetMultipipe returns the number of pfPipes configured.
After pfConfig, stage configuration callbacks may be specified with
pfStageConfigFunc and triggered with pfConfigStage. Configuration
Page 12
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
callbacks are typically used for process initialization, e.g, assign
non-degrading priorities and locking processes to processors or
downloading textures in the DRAW stage callback. The stageMask argument
to pfStageConfigFunc is a bitmask which identifies one or more OpenGL
Performer stages (see pfGetPID above). If >= 0, the pipe argument to
pfStageConfigFunc selects stage(s) on a particular pfPipe (
pfGetPipe(pipe) ). If pipe is < 0 it selects stages of all pfPipes. Note
that pipe is ignored for the PFPROC_ISECT, PFPROC_APP, and PFPROC_DBASE
stages since they are not associated with any pfPipe. configFunc is the
callback function to be invoked for the indicated stages.
pfGetStageConfigFunc returns the configuration function used for the
stage identified by pipe and stageMask.
pfConfigStage causes the callback functions to be invoked for the
identified stages at the start of processing the current application
frame. The current application frame gets to the next stage at the next
call to pfFrame. pipe and stageMask are treated identically as in
pfStageConfigFunc. When multiprocessing, the callback functions are
invoked in the appropriate processes.
Example 4: Stage configuration
void
configFunc(int pipe, uint stage)
{
/* Fix CULL processes to processor 1 and 3 */
if (stage == PFPROC_CULL)
sysmp(MP_MUSTRUN, 2*pipe+1);
/* Fix DRAW processes to processor 2 and 4 */
else if (stage == PFPROC_DRAW)
sysmp(MP_MUSTRUN, 2*pipe+2);
}
:
pfMultipipe(2);
pfMultiprocess(PFMP_APP_CULL_DRAW);
pfConfig();
pfStageConfigFunc(-1, PFPROC_CULL|PFPROC_DRAW, configFunc);
pfConfigStage(-1, PFPROC_CULL|PFPROC_DRAW);
pfFrame();
pfHyperpipe supports the hyperpipe hardware feature of VGXT/Skywriter and
Onyx/RealityEngine2 research systems, as well as Onyx/InfiniteReality and
Onyx2/InfiniteReality systems with the DPLEX option. n indicates the
Page 13
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
number of pfPipes that should be configured together in hyperpipe mode.
pfHyperpipe should be called once for each hyperpipe group in the system
that is used by the application.
The first pfPipe in the new hyperpipe group will be the lowest numbered
pfPipe that is not currently assigned to another hyperpipe group. This
pfPipe is the master pfPipe. The slave pfPipes are the next n-1
consecutive pfPipes. The master pfPipe manages the pfPipeWindows and
pfPipeVideoChannels for the slave pfPipes. The application need only
create or change pfPipeWindows and pfPipeVideoChannels on the master
pfPipe. Performer will ensure that most attributes are propagated to the
slave objects. Those attributes that are graphics pipe specific (i.e.,
VisualID or FBConfig) are not propagated, however.
Hyperpipes will run at a fraction of the system frame rate as defined by
pfFrameRate. For example, if the number of pipes in the hyperpipe group
is 2, then each pfPipe in the hyperpipe group will run at half the system
frame rate. Their aggregate rate will be equal to the system frame rate.
pfGetHyperpipe returns the total number of pfPipes in the hyperpipe group
in which the given pfPipe belongs. pfGetPipeHyperId returns the position
of the given pfPipe in its hyperpipe group. The following example
configures a two-pipeline hyperpipe system. In this example, the
hyperpipe group pipes are screens 1 and 2 of the X display :0. This
example also configures screen 0 as a single, non-hyperpipe pipe.
Example 5: Hyperpipe Example
pfMultipipe(3); /* need 3 pipes, 2 for hyperpipe, 1 for single */
pfHyperpipe(2); /* configure the hyperpipe (pfPipe 0 and 1) */
pfConfig(); /* configure Performer */
/* assign screens 1 and 2 to the hyperpipe pfPipes 0 and 1 */
pfPipeScreen(pfGetPipe(0), 1);
pfPipeScreen(pfGetPipe(1), 2);
/* assign screen 0 to the single pfPipe 2 */
pfPipeScreen(pfGetPipe(2), 0);
/* create the pfPipeWindow and pfChannel for the hyperpipe */
pwin = pfNewPWin(pfGetPipe(0));
/*
* config this pwin as needed
*
* if fbconfig or visualid must be assigned directly then get
* the pwin using:
* pwin = pfGetPipePWin(pfGetPipe(1), 0);
*
*/
chan = pfNewChan(pfGetPipe(0));
/*
Page 14
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
* config the channel as needed
*/
/* create the pfPipeWindow and pfChannel for the single pipe */
pwin = pfNewPWin(pfGetPipe(2));
chan = pfNewChan(pfGetPipe(2));
The hyperpipe group configuration can be queried directly from GLX (see
glXQueryHyperpipeNetworkSGIX(3) for more information). This information
can be used to map pfPipes to physical screens.
During the execution frame of various Performer processes, The APP
process sometime waits for other processes. If multiple Performer
processes run on the same CPU, this wait can cause a system slowdown.
OpenGL Performer provides minimal control over process priorities in
order to avoid this slowdown. This support is relevant only when running
in real-time priorities. Performer supports temporary changes to the
priorities of the CULL, ISECT, DBASE and COMPUTE processes: When the APP
process has to wait on another Performer process, it can temporarily
increase its priority to a fixed high priority.
pfProcessPriorityUpgrade turns priority-upgrading on or off.
pfGetProcessPriorityUpgrade returns the current priority-upgrade mode.
By default, OpenGL Performer performs no priority upgrades. Priority
upgrading is necessary only when running more than one Performer process
on the same CPU with different real-time priorities. If every Performer
process is allocated a separate CPU, or when processes sharing a CPU have
the same priority, priority upgrading isn't necessary. If Performer
fails to change a process priority once, it turns priority-upgrading off.
This can happen when not running as super-user.
pfProcessHighestPriority and pfGetProcessHighestPriority set and get the
high priority that the APP process will upgrade to. By default, this
priority is set to 87. The set priority should be higher than the
priorities of all other OpenGL Performer processes.
NOTES
Multiprocessing (forked CULL, DRAW, X Input, LPOINT, DBASE, COMPUTE,
etc.) is not supported in the single processor version of OpenGL
Performer for Linux. Only PFMP_APPCULLDRAW mode is available.
In practice, user callbacks in the intersection process call only
pfNodeIsectSegs and user callbacks in the database process uses the
pfBuffer mechanism to asynchronously create and delete scene graphs to
implement database paging.
If PFMP_DEFAULT is not used, it is up to the application to tailor the
Page 15
pfConfig(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfConfig(3pf)
number of OpenGL Performer processes to the number of processors. Care
must be taken to avoid thrashing, starvation, and deadlock.
If pfIsectFunc is called before pfConfig and the multiprocessing mode is
PFMP_DEFAULT, then pfConfig will fork the intersection process if there
are enough processors. Otherwise, you must explicitly fork the
intersection process by setting the PFMP_FORK_ISECT bit in the argument
passed to pfMultiprocess.
When using PFMP_CULLoDRAW, multipass algorithms (e.g. - landing lights on
InfiniteReality and RealityEngine) which call pfDraw more than once per
frame will not work.
BUGS
If PFMP_CULLoDRAW is used, modifications to pfChannel passthrough data
(see pfPassChanData) made by the cull callback will not be passed along
to the draw callback. However, modifications made by the application
process will still make it to both cull and draw callbacks.
PFMP_CULLoDRAW usually has no effect when OpenGL Performer is in the
free-running frame rate control mode specified by
pfPhase(PFPHASE_FREE_RUN). Instead, use PFPHASE_FLOAT or PFPHASE_LOCK.
When in PFMP_CULLoDRAW mode, the draw time recorded by OpenGL Performer
statistics does not include the time the draw process spends waiting for
the cull process to begin filling the ring buffer.
OBSOLETE
pfInitPipe is an obsolete routine for initializing the graphics subsystem
for a pfPipe. A callback function configFunc could be provided for
initializing pipe in the draw process and was used for opening windows in
the draw process for the pfPipe. This function has been obsoleted by the
pfPipeWindow primitive which can be used to configure windows in either
or both the application process and draw process, and by pfConfigStage
which provides a mechanism for initializing any OpenGL Performer process
or pfPipe stage. See the pfPipeWindow man page for more information on
creating and opening OpenGL Performer windows.
SEE ALSO
fork, m_fork, pfChannel, pfCycleBuffer, pfInit, pfIsectFunc, pfDBaseFunc,
pfPipe, pfDispListOptimizer, sproc
Page 16