Parallel Library V2 (V00180)
Parallel Library User Notes
(For PLIB version V2.0)
Craig W. Yankes
Digital Equipment Corporation
Mid-Range Systems Advanced Development
305 Foster Street (LTN2-2/H17)
Littleton, Massachusetts 01460
This document describes software being placed into the public
domain by Digital Equipment Corporation on an "as is" basis. No
commitments for support are either expressed or implied for the
software described herein or any potential future versions thereof.
Digital Equipment Corporation assumes no liability for any loss caused
by use of the software described herein or any potential future
versions thereof.
The information in this document is subject to change without
notice and should not be construed as a commitment by Digital
Equipment Corporation. Digital Equipment Corporation assumes no
responsibility for any errors that may appear in this document.
No responsibility is assumed for the use or reliability of
software on equipment that is not supplied by Digital Equipment
Corporation or its affiliated companies.
Comments or suggestions about the software described herein may
be forwarded to the name and address listed above.
Parallel Library V2 User Notes Page 2
CONTENTS
1 INTRODUCTION . . . . . . . . . . . . . . . . . . . . 3
2 SUMMARY . . . . . . . . . . . . . . . . . . . . . . 4
2.1 Subprocess Management . . . . . . . . . . . . . . 4
2.2 Memory Sharing . . . . . . . . . . . . . . . . . . 4
2.3 Process Synchronization . . . . . . . . . . . . . 4
2.4 Initialization Routines . . . . . . . . . . . . . 4
3 SUBPROCESS MANAGEMENT ROUTINES . . . . . . . . . . . 5
3.1 Plib$create_subprocesses . . . . . . . . . . . . . 5
3.2 Plib$delete_subprocesses . . . . . . . . . . . . . 6
3.3 Plib$current_image . . . . . . . . . . . . . . . . 7
4 MEMORY SHARING . . . . . . . . . . . . . . . . . . . 8
4.1 Plib$share_memory . . . . . . . . . . . . . . . . 8
4.2 Plib$share_code . . . . . . . . . . . . . . . . 10
4.3 Plib$current_pc . . . . . . . . . . . . . . . . 12
4.4 Plib$main_pid . . . . . . . . . . . . . . . . . 13
5 PROCESS SYNCHRONIZATION . . . . . . . . . . . . . 14
5.1 Plib$signal_subprocesses . . . . . . . . . . . . 14
5.2 Plib$signal_main . . . . . . . . . . . . . . . . 15
5.3 Plib$synch . . . . . . . . . . . . . . . . . . . 16
5.4 Plib$signal_and_wait . . . . . . . . . . . . . . 17
5.5 Plib$set_bit_interlocked . . . . . . . . . . . . 19
5.6 Plib$clear_bit_interlocked . . . . . . . . . . . 21
5.7 Plib$add_word_interlocked . . . . . . . . . . . 22
6 INITIALIZATION ROUTINES . . . . . . . . . . . . . 23
6.1 Plib$init_signals . . . . . . . . . . . . . . . 23
6.2 Plib$init_pagefile . . . . . . . . . . . . . . . 25
7 APPENDIX 1 - SAMPLE PROGRAM . . . . . . . . . . . 26
7.1 General Overview . . . . . . . . . . . . . . . . 26
Parallel Library V2 User Notes Page 3
1 INTRODUCTION
The Parallel Library is a set of routines that provide many of
the functions required to implement parallel programming. In general,
they are jacket routines around the appropriate VMS system service
calls and reduce the parameter lists to those predominantly required
by parallel programming.
The intended audience for these routines is the applications
programmer. Use of the Parallel Library routines does not require an
understanding of how the system services operate. This document will
not attempt to be a "how to" manual for parallel programming, but
rather will explain the functions of these routines. A heavily
documented program will be included as a sample program to demonstrate
the potential usage of these routines.
These routines are for use with VMS Version 4.x.
Parallel Library V2 User Notes Page 4
2 SUMMARY
These routines can be categorized into 4 groups of functions.
These areas are:
2.1 Subprocess Management
Parallelism is usually implemented under a main process /
multiple subprocesses model. This group of routines assists with the
creation and deletion of the subprocesses.
2.2 Memory Sharing
Establishing a shared memory region accessible by the main
process and the subprocesses is usually a requirement for parallelism.
This group of routines provides the functionality of sharing memory
and executable code.
2.3 Process Synchronization
There are two forms of process synchronization: barrier
synchronization to control the overall flow of the program and task
assignment for the subprocess to allocate the next piece of work. The
routines in this group assist in providing these operations.
2.4 Initialization Routines
This group of routines provides various initialization functions
that are required for subsequent operations. Specifically, these
routine provide for the initialization of the paging file and the
signaling mechanisms.
Parallel Library V2 User Notes Page 5
3 SUBPROCESS MANAGEMENT ROUTINES
3.1 Plib$create_subprocesses
This routine will request that the system create the number of
subprocesses that has been specified.
Format:
istat = plib$create_subprocesses (number_of_subprocesses,
exe_name, sys_input, sys_output, return_pids)
Arguments:
number_of_subprocesses - Count of the number of subprocesses
to be started. Longword passed by reference.
exe_name - Name of the .exe file that this subprocess will
execute. Character string (maximum of 128 characters)
passed by descriptor.
sys_input - String to assign to the sys$input logical.
Character string passed by descriptor.
sys_output - String to assign to the sys$output and
sys$error logicals. Character string passed by descriptor.
return_pids - An array of NUMBER_OF_SUBPROCESSES longwords
that will return the PIDs of the created subprocesses. This
array space must be allocated by the calling process.
Return value:
The return value is whatever value is returned from the
$CREPRC system service call.
Restrictions:
Comments:
To avoid problems if the executable image disk name has
changed or is being run from a different directory, the
PLIB$CURRENT_IMAGE routine should be used to obtain the
image name.
Parallel Library V2 User Notes Page 6
3.2 Plib$delete_subprocesses
This routine uses the Delete Process system service to delete
some or all of the subprocesses.
Format:
istat = plib$delete_subprocesses (inum, ipids)
Arguments:
INUM - The number of subprocesses to delete. Longword
passed by reference.
IPIDS - Longword array of subprocess PIDs to delete. (Note,
these pids can be obtained when the subprocesses are created
by the PLIB$CREATE_SUBPROCESSES routine.) Only the first
INUM number of subprocesses will be deleted from this list.
Return value:
1 = all were deleted successfully
0 = At least one subprocess was not deleted.
Restrictions:
Comments:
Parallel Library V2 User Notes Page 7
3.3 Plib$current_image
The PLIB$CURRENT_IMAGE routine will return the name of the image
currently being executed.
Format:
istat = plib$current_image (image_name)
Arguments:
image_name - Character string of 128 characters in which the
name of the current executable image will be returned.
Return value:
The return value is the status value from the $GETJPI system
service.
Restrictions:
Comments:
This routine should be used to determine the name of the
image to be passed to the PLIB$CREATE_SUBPROCESSES routine
and minimizes the problems of images being executed from
other directories or being renamed.
Parallel Library V2 User Notes Page 8
4 MEMORY SHARING
4.1 Plib$share_memory
The PLIB$SHARE_MEMORY routine attempts to map to an existing
global section and will create the global section if it did not
previously exist.
Format:
istat = plib$share_memory (low_address, high_address,
section_name)
Arguments:
LOW_ADDRESS - The starting virtual address for the range of
memory to be shared. Longword passed by reference.
HIGH_ADDRESS - The ending virtual address for the range of
memory to be shared. Longword passed by reference.
SECTION_NAME - Name of the global section to either map to
or create.
Return value:
If the process-private page file does not have enough free
space to contain the shared memory range being requested,
the process will abort and state the size of the paging file
that is required.
The return value is that from the $CRMPSC (Create and Map
Global Section) system service.
Restrictions:
The process-private paging file must be initialized (by
calling PLIB$INIT_PAGEFILE) prior to calling this routine.
The PLIB$SHARE_CODE routine, if used in the application,
must be called prior to this routine.
Comments:
When the global section is created, it is defined as being
demand-zero and thus the entire global section is zeroed.
No attempt is made to preserve existing data in this shared
range at the time of the global section creation. Note,
this operation of zeroing the data only occurs when the
global section is created. If the main process creates it
and deposits values into it, those values are accessible to
Parallel Library V2 User Notes Page 9
the subprocesses after they have mapped to the global
section.
Two things to be careful of:
1) Since global sections are always on full page boundaries,
the memory sharing is actually done from the first byte of
the page containing the LOW_ADDRESS address to the last byte
of the page containing the HIGH_ADDRESS address. This has
the side effect that more memory is shared than what was
requested in the parameters. The sample program's comments
will show some methods to avoid the potential problems this
can create.
2) Global sections are accessible by either any process in
the creator's UIC group or by any process in the system.
This routine creates the global section to be accessible
throughout the UIC group. Be careful, therefore, that two
or more processes in the same UIC group don't accidentally
try to access a global section that has the same name! The
PLIB$MAIN_PID routine can be used to derive a
process-specific unique name that can be appended to the
Global Section name to avoid this problem.
Parallel Library V2 User Notes Page 10
4.2 Plib$share_code
The PLIB$SHARE_CODE routine will use Global Sections to share
executable code. This code sharing does not require any privileges to
implement.
Format:
istat = plib$share_code (low_address, high_address,
section_name)
Arguments:
LOW_ADDRESS - The starting virtual address for the range of
memory to be shared. Longword passed by reference.
HIGH_ADDRESS - The ending virtual address for the range of
memory to be shared. Longword passed by reference.
SECTION_NAME - Name of the global section to either map to
or create.
Return value:
If the process-private page file does not have enough free
space to contain the shared memory range being requested,
the process will abort and state the size of the paging file
that is required.
The return value is that from the $CRMPSC (Create and Map
Global Section) system service.
Restrictions:
The process-private paging file must be initialized (by
calling PLIB$INIT_PAGEFILE) prior to calling this routine.
This routine may only be called once in a program. Any
executable code to be shared should be in contiguous virtual
addresses and be set up as shareable through this one call.
Comments:
Two things to be careful of:
1) Since global sections are always on full page boundaries,
the memory sharing is actually done from the first byte of
the page containing the LOW_ADDRESS address to the last byte
of the page containing the HIGH_ADDRESS address. This has
the side effect that more memory is shared than what was
Parallel Library V2 User Notes Page 11
requested in the parameters. The sample program's comments
in will show some methods to avoid the potential problems
this can create.
2) Global sections are accessible by either any process in
the creator's UIC group or by any process in the system.
This routine creates the global section to be accessible
throughout the UIC group. Be careful, therefore, that two
or more processes in the same UIC group don't accidentally
try to access a global section that has the same name! The
PLIB$MAIN_PID routine can be used to derive a
process-specific unique name that can be appended to the
Global Section name to avoid this problem.
In some languages, FORTRAN as an example, it is not
straightforward to determine where the executable code
starts and ends. Please refer to the sample program to
demonstrate the usage of PLIB$CURRENT_PC and the "book
marker" routine to determine the range to be shared.
Parallel Library V2 User Notes Page 12
4.3 Plib$current_pc
This routine is used in conjunction with the PLIB$SHARE_CODE and
assists in determining the starting virtual address for the range to
be shared.
Format:
iaddr = plib$current_pc()
Arguments:
- none -
Return value:
The returned value in IADDR is the virtual address of where
this routine was called from.
Restrictions:
Comments:
Refer to the sample program for an explanation of how this
routine assists with the sharing of executable code.
Parallel Library V2 User Notes Page 13
4.4 Plib$main_pid
The plib$main_pid routine returns the process identification
(PID) of the parent process if called from a subprocess. If called by
a main process, it returns its own PID.
Format:
my_pid = plib$main_pid (parent_pid)
Arguments:
PARENT_PID - Character string variable of eight characters
in length in which the ascii representation of the parent
process's PID will be returned.
Return value:
0 - This routine has been called by a main process.
non-0 - This routine was called by a subprocess and the
value returned is the integer longword value of the
subprocess's own PID.
Restrictions:
Comments:
Appending the main process's PID to global section and
private page file names is an easy method of avoiding
process-to-process interactions.
The value returned in PARENT_PID is the PID of the parent
process. In an environment of a main process with multiple
subprocesses, this equates to returning the PID of the main
process. Be careful if subprocesses are creating other
subprocesses since the second level subprocesses will not
receive the PID of the main process but rather of its
parent!
Parallel Library V2 User Notes Page 14
5 PROCESS SYNCHRONIZATION
5.1 Plib$signal_subprocesses
The PLIB$SIGNAL_SUBPROCESSES routine is used to awaken the
subprocesses and to tell them which parallel section to execute.
Format:
istat = plib$signal_subprocesses (section_number,
wait_option)
Arguments:
SECTION_NUMBER - A longword whose value will be passed to
each subprocess when they are awakened. Passed by
reference.
WAIT_OPTION - This argument specifies whether the main
process should wait for the subprocesses to report
completion before continuing execution. The options are:
0 - Don't wait for the subprocesses to report
completion. Using this option will request that this
routine returns to the calling routine immediately
after awakening the subprocesses.
non-0 - Wait for the subprocesses to report completion.
With this option, this routine will not return to the
calling routine until the subprocesses have signaled
their completion.
Return value:
This routine will always return a 1.
Restrictions:
The PLIB$INIT_SIGNALS routine must be called prior to using
this routine.
Comments:
The section_number argument is normally used to instruct the
subprocesses as to which section of code to execute. Since
the Parallel Library routines don't do anything with this
value except to pass it to the subprocesses, however, this
longword can be used for any purpose.
Parallel Library V2 User Notes Page 15
5.2 Plib$signal_main
The PLIB$SIGNAL_MAIN routine is used by the subprocesses to
report their completion to the main process. This routine will not
return until the next time the main process has awakened the
subprocesses by the PLIB$SIGNAL_SUBPROCESSES routine.
Format:
istat = plib$signal_main (next_part)
Arguments:
NEXT_PART - This argument is how the subprocesses receive
the SECTION_NUMBER value that the main process specified in
PLIB$SIGNAL_SUBPROCESSES.
Return value:
This routine will return a 1 in all cases.
Restrictions:
The PLIB$INIT_SIGNALS routine must be called prior to using
this routine.
Comments:
Every subprocess is to call this routine when it has
completed its own functions. The main process will be
signaled only when every subprocess has called this routine.
Parallel Library V2 User Notes Page 16
5.3 Plib$synch
This routine is used by the main process to determine when the
subprocesses have completed their work if the subprocesses were
awakened with the NO_WAIT option in PLIB$SIGNAL_SUBPROCESSES.
Format:
istat = plib$synch ()
Arguments:
- none -
Return value:
This routine returns a 1 in all cases.
Restrictions:
The PLIB$INIT_SIGNALS routine must be called prior to using
this routine.
Comments:
This routine is used to pause the main process until the
subprocesses have signaled completion if the main process
has been executing at the same time. This can be caused by
two situations:
1) The main process awoke the subprocesses using the NO_WAIT
option to PLIB$SIGNAL_SUBPROCESSES, or,
2) The subprocesses were just created.
In either case, the main process will eventually reach a
point where it must know that the subprocesses have
completed their previous task (or are ready in the case of
creating the subprocesses) before the main process can
continue. The PLIB$SYNCH routine provides this
functionality and will pause the main process until the
subprocesses have all reported completion by calling
PLIB$SIGNAL_MAIN.
Parallel Library V2 User Notes Page 17
5.4 Plib$signal_and_wait
This routine can be used to signal the subprocesses and wait for
them to report their completion. NOTE - This routine is being kept in
the V2 of the Parallel Library only for backwards compatibility with
V1. With the ease of using the V2 routines, it is fully expected that
PLIB$SIGNAL_SUBPROCESSES, PLIB$SIGNAL_MAIN and PLIB$SYNCH would be
used instead of PLIB$SIGNAL_AND_WAIT.
Format:
istat = plib$signal_and_wait (sub_ef, main_ef)
Arguments:
SUB_EF - Longword passed by reference whose value is an
event flag number to be set to awaken the subprocesses.
MAIN_EF - Longword passed by reference whose value is the
event flag that the subprocesses will set to reawaken the
main process.
Return value:
This routine always returns a 1.
Restrictions:
Comments:
This routine has the effect of setting the event flag
specified in SUB_EF, wait for the event flag specified in
MAIN_EF to be set and then clear both event flags before
returning.
Be careful when using this routine to avoid the "sticky
flag" problem. For example, if the subprocesses will always
be awakened by event flag 64 and will awaken the main
process with 65, the following will happen:
Subprocesses wait for event flag 64.
The main process sets 64 and waits for 65.
The subprocesses awake, perform their action, set event
flag 65 to report completion and wait for 64.
The subprocesses immediately continue since event flag
64 is still set.
Parallel Library V2 User Notes Page 18
The "sticky flag" problem is that there are no guaranteed
ways of clearing event flag 64 that doesn't have timing
windows. To get around this, the program can use two
separate event flags to awaken the subprocesses - the first
time they wait for 64 and the next time they wait for 66,
for example, with the "next flag" continually toggling back
and forth. This is not hard to code once it is conceptually
understood, but is prone to errors. The hassles involved in
using this routine was the basis for creating the
PLIB$SIGNAL_MAIN and PLIB$SIGNAL_SUBPROCESSES routines that
perform this event flag toggling automatically.
Parallel Library V2 User Notes Page 19
5.5 Plib$set_bit_interlocked
This routine uses the VAX BBSSI instruction to set the least
significant bit of the first argument interlocked. This routine will
continually attempt to set the bit until it has been successful.
Format:
istat = plib$set_bit_interlocked (flag, [loop_count,
entry_count])
Arguments:
FLAG - Longword passed by reference whose least significant
bit is to be set using the VAX BBSSI interlocked bit setting
instruction.
LOOP_COUNT - A longword passed by reference whose value is
incremented every time the bit setting is attempted.
ENTRY_COUNT - A longword passed by reference whose value is
incremented once upon calling this routine.
Return value:
This routine always returns 1 since it does not return until
the bit setting operation has been successful.
Restrictions:
Comments:
This routine is used to implement critical sections and
permits only one one process to enter the critical section
at a time. A coding example is:
istat = plib$set_bit_interlocked (flag, loop_count,
entry_count)
my_variable = shared_variable
shared_variable = shared_variable + 10
istat = plib$clear_bit_interlocked (flag)
If two or more processes try to enter this critical section
at the same time, only one will be permitted to enter since
only one process could (by definition of the VAX interlocked
instructions) have set the bit in the shared FLAG variable
and return from this routine. The other process will remain
Parallel Library V2 User Notes Page 20
in the PLIB$SET_BIT_INTERLOCKED routine until the first has
cleared the bit via the PLIB$CLEAR_BIT_INTERLOCKED routine.
The loop_count and entry_count arguments are useful in
determining how often two or more processes are blocking
each other for access to the critical sections. The numbers
individually have little meaning, but comparing the ratio
between the two can yield valid performance and bottleneck
information. ***** Since these numbers are only valid when
compared together, they must either both be in the argument
list or neither. *****
Examples of the two possible calling formats are:
istat = plib$set_bit_interlocked (flag)
istat = plib$set_bit_interlocked (flag, loop_count,
entry_count)
In the first example, note the absence of an extra comma to
denote defaulted arguments.
Parallel Library V2 User Notes Page 21
5.6 Plib$clear_bit_interlocked
This routine uses the VAX BBCCI instruction to clear the least
significant bit of the argument.
Format:
istat = plib$clear_bit_interlocked (flag)
Arguments:
FLAG - Longword passed by reference whose least significant
bit is to be cleared using the VAX BBCCI interlocked
instruction.
Return value:
1 - The bit was set upon calling this routine and has been
cleared.
0 - The bit was not set upon calling this routine.
Restrictions:
Comments:
As in the coding example at the end of the
PLIB$SET_BIT_INTERLOCKED description, this routine is used
to clear the flag bit to permit other processes to enter
into the critical section. And yes, setting FLAG = 0 will
accomplish the same function. However, the error checking
that is done by this routine is generally worth the added
overhead of the subroutine call. For example, accidentally
saying FLOG = 0 would be a fatal algorithmic error in that
the FLAG variable will not be cleared but there would
obviously not be any compiler errors. Using this routine
and accidentally typing FLOG instead of FLAG will generate
the error return status since FLOG will probably be zero
upon entry.
Parallel Library V2 User Notes Page 22
5.7 Plib$add_word_interlocked
This routine uses the VAX Add Aligned Word Interlocked
instruction (ADAWI) to perform an interlocked addition.
Format:
istat = plib$add_word_interlocked (add_value, sum_value)
Arguments:
ADD_VALUE - The word value (passed by reference) to be added
to the SUM_VALUE.
SUM_VALUE - The word value (passed by reference) to which
the ADD_VALUE argument will be added to.
Return value:
0 - The final answer in SUM_VALUE was zero.
1 - The final answer in SUM_VALUE was non-zero.
Restrictions:
Comments:
Be careful when using this routine that the program does not
use the answer that is in SUM_VALUE. The problem is that
the addition itself is performed interlocked, but that the
memory fetching to use this value is not part of the
interlocked sequence and thus another process could have
already modified it by another call to
PLIB$ADD_WORD_INTERLOCKED. (The return value for this
routine is based upon the condition codes at the end of the
ADAWI instruction and thus can be trusted.)
This routine does have a useful purpose, however, and that
is to implement count-down semaphores where the only
interest is when the final value is zero. Testing the
return value instead of SUM_VALUE can be used to check for
this condition.
Parallel Library V2 User Notes Page 23
6 INITIALIZATION ROUTINES
6.1 Plib$init_signals
Format:
istat = plib$init_signals (ef_start, num, proc_num)
Arguments:
EF_START - This argument specifies the first of three
consecutive event flag numbers that the various Parallel
Library routines can use to perform the subprocess
synchronization. Longword passed by reference.
NUM - The number of subprocesses that are going to be used
in this application. Longword passed by reference.
PROC_NUM - This argument is returned from the routine and
specifies if the calling process was the main process or a
subprocess. Possible values:
0 - This routine was called from a main process.
>0 - This routine was called by a subprocess. Each
subprocess will receive a unique number in the range of
1 to NUM based upon the order of calling the routine.
Return value:
The possible return values are:
1 - Success.
0 - An illegal range of event flags was specified.
Anything else - Return value from a system service.
Restrictions:
Since the event flags must be shared, the entire event flag
cluster that contains the specified event flags is set up as
shared between the main process and the subprocesses. To
minimize the errors caused by accidentally sharing event
flags, specifying an event flag range that crosses a cluster
boundary is illegal.
This routine (along with the rest of the Parallel Library)
require exclusive access to a PSECT (FORTRAN common block)
named PLIB_COM. This common block will be set up as a
shared global section whose name is the eight character PID
of the main process appended to "PLIBSH".
Parallel Library V2 User Notes Page 24
This routine must be called after PLIB$INIT_PAGEFILE has
been called and after the optional call to PLIB$SHARE_CODE.
(There are no restrictions on who to call first, this
routine or calls to PLIB$SHARE_MEMORY.)
Comments:
To clarify the required calling sequence, this is the order
in which the functions must be called:
1) PLIB$INIT_PAGEFILE must be called first.
2) PLIB$SHARE_CODE is optionally called next and can
only be called once.
3) The call to PLIB$INIT_SIGNALS and the various
optional calls to PLIB$SHARE_MEMORY can occur in any
order.
Parallel Library V2 User Notes Page 25
6.2 Plib$init_pagefile
The PLIB$INIT_PAGEFILE routine initializes the access to the
process private paging file and will, optionally, create the page
file.
Format:
istat = plib$init_pagefile (page_file_name, create_option)
Arguments:
PAGE_FILE_NAME - The name of the page file to use.
Character variable of up to 128 characters passed by
reference.
CREATE_OPTION - Defines if this routine is to create a new
page file or to use an existing file. Values are:
0 - Use the existing file specified in PAGE_FILE_NAME.
>0 - Create a new page file called PAGE_FILE_NAME with
a size of CREATE_OPTION number of blocks.
Return value:
1 - Success
0 - Error encountered initializing the page file.
Restrictions:
Comments:
This routine, along with the other initialization routines,
can be safely called from subprocesses with the appropriate
action being taken. For example, if this routine is called
by the main process and multiple subprocesses and requests
that a new page file be created, only one page file will be
created.
To minimize problems of multiple processes being run from
the same directory and trying to use the same filename, the
suggestion is to append the main process's PID to the
filename just as with the global section names.
Parallel Library V2 User Notes Page 26
7 APPENDIX 1 - SAMPLE PROGRAM
Parallel Library Userguide
Sample Program Summary
7.1 General Overview
The sample program included as part of the Parallel Library
originated in a real paralleled program, but has had all of the "real
work" removed to leave behind only the constructs required to
implement and coordinate the parallelism. Error checking of the
Parallel Library routine return statuses has also been eliminated to
minimize the amount of non-coordination code. There are two parallel
sections in this program, both of which do a few lines of code once a
task has been allocated. (This program is quite heavily commented to
explain various parallelism concepts. Without comments it is roughly
one printed page. With comments, it is 12 pages long!)
The program is called SAMPLE.FOR and is included as part of the
Parallel Library package.
*** Note *** The functions in these parallel sections are
very simple for demonstration purposes and probably will
never be replicated in a real program.
The parallel sections of code that the subprocesses will execute
are:
1) The first section contains 100 tasks. The only work involved
for the task is writing out the task number and which subprocess
executed it.
2) The second section copies a 100 element array into another 100
element array in ten tasks of ten locations each.
As mentioned, these are not representative of real world
programs, but the desire was to minimize the lines of code that
weren't directly involved with coordinating the parallelism.
Parallel Library V2 User Notes Page 27
The program flow is as follows (assuming chronological order in
the vertical axis):
Main process Subprocesses
------------ ------------
1) Is executed.
2) Creates the shared memory
global section and the
shared event flags.
3) Creates the subprocesses. Are created.
4) Waits for the subprocesses Maps to the existing shared
to report in as ready. memory global section and
the shared event flags.
5) Reports back when all
subprocesses are ready.
Waits for main to signal
work.
6) Main awakens. Sets up for
and signals section 1 to be
executed.
7) Main waits for subs to report Subprocesses awaken and
completion of section 1. execute section 1.
8) Subprocesses perform section
1 and report when all are
finished. Wait for main
to signal the next work.
9) Main awakens and executes
some dummy single-stream
code to show where it could
be done between sections 1
and 2.
9) Main repeats steps 6 Subprocesses repeat steps
through 8 for section 2. 6 through 8 for section
2.
10) Main deletes the subprocesses
and exits.
By examining this program, the standard flow of a parallel
program should be observable. The reader is directed to look at the
sample program with the flow outline given above to observe how the
Parallel Library routines can be used in a parallel application. (Any
comment line starting with two asterisks (c**) has been added to this
Parallel Library V2 User Notes Page 28
demonstration program specifically to help explain the background
concepts.)
Click on FTP to download from the FTP archives.
![[FTP]](http://www2.encompassus.org/hidedecus/graphics/i_ftp.gif)