OpenMP support

From Free Pascal wiki
Revision as of 22:33, 25 July 2006 by V.hoefler (talk) (Some early idea of implementing OpenMP in clean Pascal syntax.)

What is OpenMP?

OpenMP is an API accessed by language directives to do multi threaded programming, see also http://www.openmp.org. Currently, there is only OpenMP syntax defined for C and Fortran. This page tries to collect some stuff to settle down pascal syntax for it.

Pascal syntax for OpenMP

Proposal 1

Foreword

At first, I must admit that some parts of the OpenMP specification I still don't understand. They did a terrible good job throwing away all common terms ever used in multi threading context, and invented their own ones.

Syntax vs. Compiler directives

OpenMP for C and C++ is implemented by using compiler directives mainly due to the reasons of source code compatibility (or: standards compliance). So a conforming program is intended to behave the same regardless if the actual compiler compiling the program supports those special pragmas or not.

For FreePascal I don't think this is the way to go, because first it changes comments into code and second, it makes the program far less readable. For C programs this doesn't seem to be an issue, if you get my meaning. But in my opinion, readability is a far more important issue than compatibility to older/different compilers. If all else fails, a preprocessor could be provided to strip out the parallel specific stuff, as has been suggested by Marco.

Well, enough talk, I start with the easier directives which are luckily the more fundamental ones.

parallel

The parallel construct can only be used for a structured block. So in Pascal it should be followed by a begin/end pair anyway. If this could be made a requirement (no one-liners allowed), even the clauses that come with the parallel construct can mostly be done in a clean and readable way. So if you take a look at the A.4.1.c example of the OpenMP 2.5 specification, the Pascal version could look like this:

  procedure SubDomain (var x       : array of Float;
                           istart  : Integer;
                           ipoints : Integer)
  var
     i : Integer;
  begin
     for i := 0 to ipoints - 1 do
        x[istart + i] := 123.456;
  end {SubDomain};
  
  procedure Sub (var x : array of Float);
  // Variables declared here should have shared context.
  // This would include the function's parameters then...
  begin
     parallel
        // Variables declared here have private context.
        iam     : Integer;
        nt      : Integer;
        ipoints : Integer;
     begin // of parallel section
        iam := OMP.Get_Thread_Num;  // OMP library calls.
        nt  := OMP.Get_Num_Threads;
        
        ipoints := Length (x) div nt; // size of partition
        istart  := iam * ipoints;     // starting array index
        
        if iam = Pred (nt) then
           ipoints := Length (x) - istart; // last thread may do more
        
        SubDomain (x, istart, ipoints);
     end {parallel};
  end {Sub};
  
  var
     arr = array[0 .. 9999] of Float;
  begin  // Main program
     Sub (arr, 10000);
  end.


More constructs

To be continued...

V.hoefler


Proposal 2

Proposal 2

<not yet done>