xiangyu / aparapi

Automatically exported from code.google.com/p/aparapi
Other
0 stars 0 forks source link

Support @Parallel for loops or create new "parfor" language feature #76

Open GoogleCodeExporter opened 9 years ago

GoogleCodeExporter commented 9 years ago
I want to make sure we capture a new feature we've been talking about in 
Aparapi which is inspired by a similar feature in OpenMP.

Option 1:

for(@Parallel int i=0; i<value; i++)

Option 2:

parfor(int i=0; i<value; i++)

Ideally this new construct would create a Kernel behind the scenes with the 
appropriate information. The scope of this request is obviously huge, but baby 
steps will still be very nice to work on implement

Original issue reported on code.google.com by ryan.lam...@gmail.com on 29 Oct 2012 at 6:30

GoogleCodeExporter commented 9 years ago
How we can use annotations in For loops today in a backwards-compatible form 
while waiting for OpenJDK 8:

http://code.google.com/p/jsr308-langtools/wiki/AnnotationsOnStatements
http://types.cs.washington.edu/jsr308/

Original comment by ryan.lam...@gmail.com on 29 Oct 2012 at 6:33

GoogleCodeExporter commented 9 years ago
I like #1, clearly #2 is beyond the scope of Aparapi as it requires a Java 
language change.  The Ateji guys (http://www.ateji.com/) tried to achieve #2 
using a pre-processor stage, but this really does get you into the javac/IDE 
toolchain business and that is hard. 

As project lambda marches forward, I actually do think that #1 is 'almost' 
unnecessary.  I think that Parallel.forEach(range, SAMtype) where the 
implementation of SAMtype would  be your for loop body and range would define 
the global range. 

Even #1 is tricky at runtime without either a customized classloader with 
bytecode re-writing or some APT trickery to transform the AST at compile time.  
So my advice would be to converge with the project lambda guys and use the 
lamda style.

If you look at the 'mock lambda' branch I have started playing with this.  
Indeed there is a functioning Aparapi.forEach(range, SAMtype) style 
implementation (JTP at present) working mandel example.  I hope to have Lambda 
to OpenCL working in a few weeks. 

Gary  

Original comment by frost.g...@gmail.com on 29 Oct 2012 at 7:15

GoogleCodeExporter commented 9 years ago
Gary,

A couple of things:

- I think the links I provided above touch on your thoughts briefly...adding 
loop bodies as an inner class for a parameter. They have some arguments against 
that approach, although the Lambdas approach may be cleaner. See 
InParallel.reduce example. Their use of @ParallelAccumulator and 
@Parallelizable almost identically mirrors the approach we've been discussing 
offline.

- We can include JST-308 features by simply including the above linked 
libraries into Aparapi.

- It is going to take a long time before we start using Java 7 full-time on our 
projects, much less Java 8. But since we can get Aparapi approved, then we 
could get features that are included in Aparapi approved as well.

Original comment by ryan.lam...@gmail.com on 29 Oct 2012 at 9:24

GoogleCodeExporter commented 9 years ago
Don't get me wrong I am a big fan of extending Annotations to include 
annotations on arbitary statements or even on blocks, and would love to see it 
(BTW I argued for this case with the Ateji guys to allow them to avoid 
pre-processing). 

Sadly I thought that the notion of annotating other than on fields/locals had 
been dropped (at least for Java 8).  Basically the classfile would need to be 
changed substantially for this.  Annotation info (in Attribute tables) are 
attached to field references in the classfile. To annotate arbitrary code would 
require being able to also add annotation information to method code attributes 
as a 'side-table' (rather like exception tables).

I don't see the classfile changes being made to support this.  

Original comment by frost.g...@gmail.com on 29 Oct 2012 at 10:19

GoogleCodeExporter commented 9 years ago
Okay, that's a bummer.

What do you think about having an annotation like this:

@Target({
      ElementType.PARAMETER,
      ElementType.FIELD,
      ElementType.LOCAL_VARIABLE
})
@Retention(RetentionPolicy.RUNTIME)
public @interface Parallel {

}

Original comment by ryan.lam...@gmail.com on 30 Oct 2012 at 12:26

GoogleCodeExporter commented 9 years ago
After some additional research and clarifications about JSR-308, then I propose 
implementing a Parallel.For and Parallel.ForEach similar to the code available 
at:

http://www.cs.gmu.edu/~rcarver/cs475/Parallel.java

For comparison purposes, C# has had this kind of parallelism built-in since C# 
4.0:

Parallel Programming in .NET
http://msdn.microsoft.com/en-us/library/dd460693.aspx

Task Parallel Library (TPL)
http://msdn.microsoft.com/en-us/library/dd460717.aspx

Data Parallelism
http://msdn.microsoft.com/en-us/library/dd537608.aspx

Task Parallelism
http://msdn.microsoft.com/en-us/library/dd537609.aspx

Original comment by ryan.lam...@gmail.com on 28 Nov 2012 at 1:30

GoogleCodeExporter commented 9 years ago
Steven and I have been discussing this issue. We have another project that we 
will be looking to integrate Aparapi, but would also like to just have access 
to the parallelization aspect of Aparapi's API at some points, even if the code 
is not Aparapi or GPU-friendly.

So, we're looking into creating the following without Lambdas as we need the 
solution to use JDK 7:

Parallel.For()
Parallel.ForEach()

Then we're thinking about expanding this to include possibly the following:

Parallel.For(1DLoopStart, 1DLoopEnd, Kernel/LoopBody)
Parallel.For(1DLoopStart, 1DLoopEnd, 2DLoopStart, 2DLoopEnd, Kernel/LoopBody)

etc.

We've also thought about using the Fork/Join framework directly, but would like 
to use Aparapi wrappers if possible.

Which brings up another point...Should we force Aparapi to require JDK 7 and 
start using features such as the Fork/Join framework? We can obviously create 
equally as parallel code by hand, but it's just a thought.

Original comment by ryan.lam...@gmail.com on 30 Nov 2012 at 6:59

GoogleCodeExporter commented 9 years ago
I like the Parallel.For() it maps pretty cleanly on the work that Eric Caspole 
and myself have been looking at for Sumatra, and also, is fairly similar to the 
API in the 'MockLambda' branch. 

We might want to think how the 'lambda' receives it's identity (1D, 2D or 3D) 

One way is to pass the id into the lambda (I like this ;) ) So (using the 1D 
form) 

Parallel.For (from, to, (int id)->{body uses id as they would getGlobalId() });

Another option is  to pass an ID object into the lambda so it can be queried. 

Parallel.For (from, to, (Id1D id)->{body  uses id->getGlobalId() also 
id->getGroupId() etc) 

I must confess that we may end up using the Range type object (or may also wish 
to support it!) allowing 

Parallel.For (Range2D range, (Id2D id)->{body})

Where the actual range can be extracted from the the id

id->getRange()->getGlobalSize(0);

Gary

Original comment by frost.g...@gmail.com on 1 Dec 2012 at 1:04