<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	
	xmlns:georss="http://www.georss.org/georss"
	xmlns:geo="http://www.w3.org/2003/01/geo/wgs84_pos#"
	>

<channel>
	<title>c# LAPACK GPU Archives - CenterSpace</title>
	<atom:link href="https://www.centerspace.net/tag/c-lapack-gpu/feed" rel="self" type="application/rss+xml" />
	<link>https://www.centerspace.net/tag/c-lapack-gpu</link>
	<description>.NET numerical class libraries</description>
	<lastBuildDate>Wed, 02 Mar 2016 18:39:25 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.1.1</generator>
<site xmlns="com-wordpress:feed-additions:1">104092929</site>	<item>
		<title>NMath Premium&#8217;s new Adaptive GPU Bridge Architecture</title>
		<link>https://www.centerspace.net/gpu-math-csharp</link>
					<comments>https://www.centerspace.net/gpu-math-csharp#respond</comments>
		
		<dc:creator><![CDATA[Paul Shirkey]]></dc:creator>
		<pubDate>Mon, 13 Oct 2014 16:35:01 +0000</pubDate>
				<category><![CDATA[NMath Premium]]></category>
		<category><![CDATA[.NET GPU]]></category>
		<category><![CDATA[C# GPU]]></category>
		<category><![CDATA[c# LAPACK GPU]]></category>
		<category><![CDATA[C# Nvidia GPU]]></category>
		<category><![CDATA[math gpu]]></category>
		<category><![CDATA[math gpu csharp]]></category>
		<category><![CDATA[NMath GPU]]></category>
		<category><![CDATA[Offloading to GPU]]></category>
		<guid isPermaLink="false">http://www.centerspace.net/blog/?p=5295</guid>

					<description><![CDATA[<p>The most release of NMath Premium 6.0 is a major upgrade to the GPU API and it enables users to easily use multiple installed NVIDIA GPU's.  As always, using NMath Premium to leverage GPU's never requires any kernel-level GPU programming or other specialized GPU programming skills.  In the following article, after introducing the new GPU bridge architecture, we'll discuss each of the new API features separately with code examples.</p>
<p>The post <a rel="nofollow" href="https://www.centerspace.net/gpu-math-csharp">NMath Premium&#8217;s new Adaptive GPU Bridge Architecture</a> appeared first on <a rel="nofollow" href="https://www.centerspace.net">CenterSpace</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>The most recent release of NMath Premium 6.0 is a major update which includes an upgraded optimization suite, now backed by the Microsoft Solver Foundation, a significantly more powerful GPU-bridge architecture, and a new class for cubic smoothing splines. This blog post will focus on the new API for doing computation on GPU&#8217;s with NMath Premium. </p>
<p>The adaptive GPU bridge API in NMath Premium 6.0 includes the following important new features.</p>
<section>
<ul>
<li>Support for multiple GPU&#8217;s</li>
<li>Automatic tuning of the CPU&#8211;GPU adaptive bridge to insure optimal hardware usage.</li>
<li>Per-thread control for binding threads to GPU&#8217;s.</li>
</ul>
</section>
<p>As with the first release of NMath Premium, using NMath to leverage massively-parallel GPU&#8217;s never requires any kernel-level GPU programming or other specialized GPU programming skills. Yet the programmer can easily take as much control as needed to route executing threads or tasks to any available GPU device. In the following, after introducing the new GPU bridge architecture, we&#8217;ll discuss each of these features separately with code examples.</p>
<p>Before getting started on our NMath Premium tutorial it&#8217;s important to consider your test GPU model.  While many of NVIDIA&#8217;s GPU&#8217;s provide a good to excellent computational advantage over the CPU, not all of NVIDIA&#8217;s GPU&#8217;s were designed with general computing in mind. The &#8220;NVS&#8221; class of NVIDIA GPU&#8217;s (such as the NVS 5400M) generally perform very poorly as do the &#8220;GT&#8221; cards in the GeForce series. However the &#8220;GTX&#8221; cards in the <a href="http://www.geforce.com/hardware" target="_blank">GeForce series</a> generally perform well, as do the Quadro Desktop Produces and the Tesla cards. While it&#8217;s fine to test NMath Premium on any NVIDIA, testing on inexpensive consumer grade video cards will rarely show any performance advantage.</p>
<h3>NMath&#8217;s GPU API Basics</h3>
<p>With NMath there are three fundamental software entities involved with routing computations between the CPU and GPU&#8217;s: GPU hardware devices represented by <code>IComputeDevice</code> instances, the <code>Bridge</code> classes which control when a particular operation is sent to the CPU or a GPU, and finally the <code>BridgeManager</code> which provides the primary means for managing the devices and bridges.</p>
<p>These three entities are governed by two important ideas.</p>
<ol>
<li><code>Bridges</code> are assigned to compute devices and there is a strict one-to-one relationship between each <code>Bridge</code> and <code>IComputeDevice</code>. Once assigned, the bridge instance governs when computations will be sent to it&#8217;s paired GPU device or the CPU.</li>
<li>Executing threads are assigned to devices; this is a many-to-one relationship. Any number of threads can be routed to a particular compute device.</li>
</ol>
<p>Assigning a <code>Bridge</code> class to a device is one line of code with the <code>BridgeManager</code>.</p>
<pre lang="csharp">BridgeManager.Instance.SetBridge( BridgeManager.Instance.GetComputeDevice( 0 ), bridge );</pre>
<p>Assigning a thread, in this case the <code>CurrentThread</code>, to a device is again accomplished using the <code>BridgeManager</code>.</p>
<pre lang="csharp">IComputeDevice cd = BridgeManager.Instance.GetComputeDevice( 0 );
BridgeManager.Instance.SetComputeDevice( cd, Thread.CurrentThread );</pre>
<p>After installing NMath Premium, the default behavior will create a default bridge and assign it to the GPU with a device number of 0 (generally the fastest GPU installed). Also by default, all unassigned threads will execute on device 0. This means that out of the box with no additional programming, existing NMath code, once recompiled against the new NMath Premium assemblies, will route all appropriate computations to the device 0 GPU. All of the follow discussions and code examples are ways to refine this default behavior to get the best performance from your GPU hardware.</p>
<h3>Math on Multiple GPU&#8217;s Supported</h3>
<p>Currently only the NVIDIA GPU with a device number 0 is supported by NMath Premium, this release removes that barrier. With version 6, work can be assigned to any installed NVIDIA device as long as the device drivers are up-to-date.</p>
<p>The work done by an executing thread is routed to a particular device using the <code>BridgeManager.Instance.SetDevice()</code> as we saw in the example above. Any properly configured hardware device can be used here including any NVIDIA device and the CPU. The CPU is simply viewed as another compute device and is always assigned a device number of -1.</p>
<pre lang="csharp" line="1">var bmanager = BridgeManager.Instance;

var cd = bmanager .GetComputeDevice( -1 );
BridgeManager.Instance.SetComputeDevice( cd, Thread.CurrentThread );
....
cd = bmanager .GetComputeDevice( 2 );
BridgeManager.Instance.SetComputeDevice( cd, Thread.CurrentThread );</pre>
<p>Lines 3 &#038; 4 first assign the current thread to the CPU device (no code on this thread will run on any GPU) and then in lines 6 &#038; 7 the current thread is switched to the GPU device 2.  If an invalid compute device is requested a null <code>IComputeDevice</code> is returned.  To find all available computing devices, the <code>BridgeManager</code> offers an array of <code>IComputeDevices</code> which contains all detected compute devices <em>including the CPU</em>, called <code>IComputeDevices Devices[]</code>. The number of detected GPU&#8217;s can be found using the property <code>BridgeManager.Instance.CountGPU</code>.</p>
<p>As an aside, keep in mind that PCI slot numbers do not necessarily correspond to GPU device numbers. NVIDIA assigns the device number 0 to the fastest detected GPU and so installing an additional GPU into a machine may renumber the device numbers for the previously installed GPU&#8217;s.</p>
<h3>Tuning the Adaptive Bridge</h3>
<p>Assigning a <code>Bridge</code> to a GPU device doesn&#8217;t necessarily mean that all computation routed to that device will run on that device. Instead, the assigned <code>Bridge</code> acts as an intermediary between the CPU and the GPU and moves the larger problems to the GPU where there&#8217;s a speed advantage and retains the smaller problems on the CPU. NMath has a built-in default bridge, but it may generate non-optimal run-times depending on your hardware or your customers hardware configuration. To improved the hardware usage and performance a bridge can be tuned once and then persisted to disk for all future use.</p>
<pre lang="csharp">// Get a compute device and a new bridge.
IComputeDevice cd = BridgeManager.Instance.GetComputeDevice( 0 );
Bridge bridge = BridgeManager.Instance.NewDefaultBridge( cd );

// Tune this bridge for the matrix multiply operation alone. 
bridge.Tune( BridgeFunctions.dgemm, cd, 1200 );

// Or just tune the entire bridge.  Depending on the hardware and tuning parameters
// this can be an expensive one-time operation. 
bridge.TuneAll( cd, 1200 );

// Now assign this updated bridge to the device.
BridgeManager.Instance.SetBridge( cd, bridge );

// Persisting the bridge that was tuned above is done with the BridgeManager.  
// Note that this overwrites any existing bridge with the same name.
BridgeManager.Instance.SaveBridge( bridge, @".\MyTunedBridge" );

// Then loading that bridge from disk is simple.
var myTunedBridge = BridgeManager.Instance.LoadBridge( @".\MyTunedBridge" );</pre>
<p>Once a bridge is tuned it can be persisted, redistributed, and used again. If three different GPU&#8217;s are installed this tuning should be done once for each GPU and then each bridge should be assigned to the device it was tuned on. However if there are three identical GPU&#8217;s the tuning need be done only once, then persisted to disk, and later assigned to all identical GPU&#8217;s. Bridges assigned to GPU devices for which it wasn&#8217;t tuned will never result in incorrect results, only possibly under performance of the hardware.</p>
<h3>Thread Control</h3>
<p>Once a bridge is paired to a device, threads may be assigned to that device for execution. This is not a necessary step as all unassigned threads will run on the default device (typically device 0). However, suppose we have three tasks and three GPU&#8217;s, and we wish to use a GPU per task.  The following code does that.</p>
<pre lang="csharp">...
IComputeDevice gpu0= BridgeManager.Instance.GetComputeDevice( 0 );
IComputeDevice gpu1 = BridgeManager.Instance.GetComputeDevice( 1 );
IComputeDevice gpu2 = BridgeManager.Instance.GetComputeDevice( 2 );

if( gpu0 != null && gpu1 != null && gpu2 != null)
{
   System.Threading.Tasks.Task[] tasks = new Task[3]
   {
      Task.Factory.StartNew(() => Task1Worker(gpu0)),
      Task.Factory.StartNew(() => Task2Worker(gpu1)),
      Task.Factory.StartNew(() => Task2Worker(gpu2)),
   };

   //Block until all tasks complete.
   Task.WaitAll(tasks);
}
...</pre>
<p>This code is standard C# code using the <a href="https://msdn.microsoft.com/en-us/library/dd460717(v=vs.110).aspx" target="_blank">Task Parallel Library</a> and contains no NMath Premium specific API calls outside of passing a GPU compute device to each task. The task worker routines have the following simple structure.</p>
<pre lang="csharp">private static void Task1Worker( IComputeDevice cd  )
  {
      BridgeManager.Instance.SetComputeDevice( cd );

      // Do Work here.
  }</pre>
<p>The other two task workers are identical outside of whatever useful computing work they may be doing.</p>
<p>Good luck and please post any questions in the comments below or just email us at support AT centerspace.net we&#8217;ll get back to you.</p>
<p>Happy Computing,</p>
<p>Paul</p>
<p>The post <a rel="nofollow" href="https://www.centerspace.net/gpu-math-csharp">NMath Premium&#8217;s new Adaptive GPU Bridge Architecture</a> appeared first on <a rel="nofollow" href="https://www.centerspace.net">CenterSpace</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://www.centerspace.net/gpu-math-csharp/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
		<post-id xmlns="com-wordpress:feed-additions:1">5295</post-id>	</item>
		<item>
		<title>Distributing Parallel Tasks on Multiple GPU&#8217;s</title>
		<link>https://www.centerspace.net/tasks-on-gpu</link>
					<comments>https://www.centerspace.net/tasks-on-gpu#respond</comments>
		
		<dc:creator><![CDATA[Paul Shirkey]]></dc:creator>
		<pubDate>Wed, 17 Sep 2014 20:50:51 +0000</pubDate>
				<category><![CDATA[NMath Premium]]></category>
		<category><![CDATA[.NET GPU]]></category>
		<category><![CDATA[C# GPU]]></category>
		<category><![CDATA[c# LAPACK GPU]]></category>
		<category><![CDATA[C# Nvidia GPU]]></category>
		<category><![CDATA[math gpu]]></category>
		<category><![CDATA[math gpu csharp]]></category>
		<category><![CDATA[NMath GPU]]></category>
		<category><![CDATA[Offloading to GPU's]]></category>
		<guid isPermaLink="false">http://www.centerspace.net/blog/?p=5397</guid>

					<description><![CDATA[<p><img class="excerpt" alt="NMath Premium" src="/themes/centerspace/images/nmath-premium.png" /> Once Microsoft published the <code>Threading.Task</code> library with .NET 4 many programmers who never or only occasionally wrote multi-threaded code were now doing so regularly with the <code>Threading.Task</code> API.  The Task library reduced the complexity of writing threaded code and provided a several new related classes to make the process easier while eliminating some pitfalls.  In this post I'm going to show how to use the Task library with NMath Premium 6.0 to run tasks in parallel on multiple GPU's and the CPU.</p>
<p>The post <a rel="nofollow" href="https://www.centerspace.net/tasks-on-gpu">Distributing Parallel Tasks on Multiple GPU&#8217;s</a> appeared first on <a rel="nofollow" href="https://www.centerspace.net">CenterSpace</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>In this post I&#8217;m going demonstrate how to use the Task Parallel Library with NMath Premium to run tasks in parallel on multiple GPU&#8217;s and the CPU.  Back in 2012 when Microsoft released .NET 4.0 and the <code>System.Threading.Task</code> namespace many .NET programmers never, or only under duress, wrote multi-threaded code.  It&#8217;s old news now that <a href="https://msdn.microsoft.com/en-us/library/dd460693(v=vs.100).aspx" target="_blank">TPL</a> has reduced the complexity of writing threaded code by providing several new classes to make the process easier while eliminating some pitfalls.  Leveraging the TPL API together with NMath Premium is a powerful combination for quickly getting code running on your GPU hardware without the burden of learning complex CUDA programming techniques.</p>
<h2> NMath Premium GPU Smart Bridge</h2>
<p>The NMath Premium 6.0 library is now integrated with a new CPU-GPU hybrid-computing Adaptive Bridge&trade; Technology.  This technology allows users to easily assign specific threads to a particular compute device and manage computational routing between the CPU and multiple on-board GPU&#8217;s.  Each piece of installed computing hardware is uniformly treated as a compute device and managed in software as an immutable <code>IComputeDevice</code>;  Currently the adaptive bridge allows a single CPU compute device (naturally!) along with any number of NVIDIA GPU devices.  How NMath Premium interacts with each compute device is governed by a <code>Bridge</code> class.  A one-to-one relationship between each <code>Bridge</code> instance and each compute device is enforced.  All of the compute devices and bridges are managed by the singleton <code>BridgeManager</code> class.</p>
<figure id="attachment_5473" aria-describedby="caption-attachment-5473" style="width: 600px" class="wp-caption alignnone"><img decoding="async" src="https://www.centerspace.net/blog/wp-content/uploads/2014/04/Adaptive-Bridge.png" alt="Adaptive Bridge" width="600" class="size-full wp-image-5473" srcset="https://www.centerspace.net/wp-content/uploads/2014/04/Adaptive-Bridge.png 700w, https://www.centerspace.net/wp-content/uploads/2014/04/Adaptive-Bridge-300x186.png 300w" sizes="(max-width: 700px) 100vw, 700px" /><figcaption id="caption-attachment-5473" class="wp-caption-text">Adaptive Bridge</figcaption></figure>
<p>These three classes: the <code>BridgeManager</code>, the <code>Bridge</code>, and the immutable <code>IComputeDevice</code> form the entire API of the Adaptive Bridge&trade;.  With this API, nearly all programming tasks, such as assigning a particular <code>Action<></code> to a specific GPU, are accomplished in one or two lines of code.  Let&#8217;s look at some code that does just that:  Run an <code>Action<></code> on a GPU.</p>
<pre lang="csharp">
using CenterSpace.NMath.Matrix;

public void mainProgram( string[] args )
    {
      // Set up a Action<> that runs on a IComputeDevice.
      Action<IComputeDevice, int> worker = WorkerAction;
      
      // Get the compute devices we wish to run our 
      // Action<> on - in this case two GPU 0.
      IComputeDevice deviceGPU0 = BridgeManager.Instance.GetComputeDevice( 0 );

      // Do work
      worker(deviceGPU0, 9);
    }

    private void WorkerAction( IComputeDevice device, int input )
    {
      // Place this thread to the given compute device.
      BridgeManager.Instance.SetComputeDevice( device );

      // Do all the hard work here on the assigned device.
      // Call various GPU-aware NMath Premium routines here.
      FloatMatrix A = new FloatMatrix( 1230, 900, new RandGenUniform( -1, 1, 37 ) );
      FloatSVDecompServer server = new FloatSVDecompServer();
      FloatSVDDecomp svd = server.GetDecomp( A );
    }
</pre>
<p>It&#8217;s important to understand that only operations where the GPU has a computational advantage are actually run on the GPU.  So it&#8217;s not as though all of the code in the <code>WorkerAction</code> runs on the GPU, but only code that makes sense such as: SVD, QR decomp, matrix multiply, Eigenvalue decomposition and so forth.  But using this as a code template, you can easily run your own worker several times passing in different compute devices each time to compare the computational advantages or disadvantages of using various devices &#8211; including the CPU compute device.</p>
<p>In the above code example the <code>BridgeManager</code> is used twice: once to get a <code>IComputeDevice</code> reference and once to assign a thread (the <code>Action<>'s</code> thread in this case ) to the device.  The <code>Bridge</code> class didn&#8217;t come into play since we implicitly relied on a default bridge to be assigned to our compute device of choice.  Relying on the default bridge will likely result in inferior performance so it&#8217;s best to use a bridge that has been specifically tuned to your NVIDIA GPU.  The follow code shows how to accomplish bridge tuning.</p>
<pre lang="csharp">
  // Here we get the bridge associated with GPU device 0.
  var cd = BridgeManager.Instance.GetComputeDevice( 0 );
  var bridge = (Bridge) BridgeManager.Instance.GetBridge( cd );

  // Tune the bridge and save it.  Turning can take a few minutes.
  bridge.TuneAll( device, 1200 );
  bridge.SaveBridge("Device0Bridge.bdg");
</pre>
<p>This bridge turning is typically a one-time operation per computer, and once done, the tuned bridge can be serialized to disk and then reload at application start-up.  If new GPU hardware is installed then this tuning operation should be repeated.  The following code snipped loads a saved bridge and pairs it with a device.</p>
<pre lang="csharp">
  // Load our serialized bridge.
  Bridge bridge = BridgeManager.Instance.LoadBridge( "Device0Bridge.bdg" );
  
  // Now pair this saved bridge with compute device 0.   
  var device0 = BridgeManager.Instance.GetComputeDevice( 0 );
  BridgeManager.Instance.SetBridge( device0, bridge );
</pre>
<p>Once the tuned bridge is assigned to a device, the behavior of all threads assigned to that device will be governed by that bridge.  In the typical application the pairing of bridges to devices done at start up and not altered again, while the assignment of threads to devices may be done frequently at runtime.</p>
<p>It&#8217;s interesting to note that beyond optimally routing small and large problems to the CPU and GPU respectively, bridges can be configured to shunt all work to the GPU regardless of problem size.  This is useful for testing and for offloading work to a GPU when the CPU if taxed.  Even if the particular problem runs slower on the GPU than the CPU, if the CPU is fully occupied, offloading work to an otherwise idle GPU will enhance performance.</p>
<h2> C# Code Example of Running Tasks on Two GPU&#8217;s </h2>
<p>I&#8217;m going to wrap up this blog post with a complete C# code example which runs a matrix multiplication task simultaneously on two GPU&#8217;s and the CPU.  The framework of this example uses the TPL and aspects of the adaptive bridge already covered here.  I ran this code on a machine with two NVIDIA GeForce GPU&#8217;s, a GTX760 and a GT640, and the timing results from this run for executing a large matrix multiplication are shown below.</p>
<pre class="code">
Finished matrix multiply on the GeForce GTX 760 in 67 ms.
Finished matrix multiply on the Intel(R) Core(TM) i7-3770 CPU @ 3.40GHz in 103 ms.
Finished matrix multiply on the GeForce GT 640 in 282 ms.

Finished all double precision matrix multiplications in parallel in 282 ms.
</pre>
<p>The complete code for this example is given in the section below.  In this run we see the GeForce GTX760 easily finished first in 67ms followed by the CPU and then finally by the GeForce GT640.  It&#8217;s expected that the GeForce GT640 would not do well in this example because it&#8217;s optimized for single precision work and these matrix multiples are double precision.  Nevertheless, this examples shows it&#8217;s programmatically simple to push work to any NVIDIA GPU and in a threaded application even a relatively slow GPU can be used to offload work from the CPU.  Also note that the entire program ran in 282ms &#8211; the time required to finish the matrix multiply by the slowest hardware &#8211; verifying that all three tasks did run in parallel and that there was very little overhead in using the TPL or the Adaptive Bridge&trade;</p>
<p>Below is a snippet of the NMath Premium log file generated during the run above.</p>
<pre class="code">
	Time 		        tid   Device#  Function    Device Used    
2014-04-28 11:22:47.417 AM	10	0	dgemm		GPU
2014-04-28 11:22:47.421 AM	15	1	dgemm		GPU
2014-04-28 11:22:47.425 AM	13	-1	dgemm		CPU
</pre>
<p>We can see here that three threads were created nearly simultaneously with thread id&#8217;s of 10, 15, &#038; 13;  And that the first two threads ran their matrix multiplies (dgemm) on  GPU&#8217;s 0 and 1 and the last thread 13 ran on the CPU.  As a matter of convention the CPU device number is always -1 and all GPU device numbers are integers 0 and greater.  Typically device number 0 is assigned to the fastest installed GPU and that is the default GPU used by NMath Premium.  </p>
<p>-Paul</p>
<h3> TPL Tasks on Multiple GPU&#8217;s C# Code </h3>
<pre lang="csharp">
public void GPUTaskExample()
    {
     
      NMathConfiguration.Init();

      // Set up a string writer for logging
      using ( var writer = new System.IO.StringWriter() )
      {

        // Enable the CPU/GPU bridge logging
        BridgeManager.Instance.EnableLogging( writer );

        // Get the compute devices we wish to run our tasks on - in this case 
        // two GPU's and the CPU.
        IComputeDevice deviceGPU0 = BridgeManager.Instance.GetComputeDevice( 0 );
        IComputeDevice deviceGPU1 = BridgeManager.Instance.GetComputeDevice( 1 );
        IComputeDevice deviceCPU = BridgeManager.Instance.CPU;

        // Build some matrices
        var A = new DoubleMatrix( 1200, 1400, 0, 1 );
        var B = new DoubleMatrix( 1400, 1300, 0, 1 );

        // Build the task array and assign matrix multiply jobs and compute devices
        // to those tasks.  Any number of tasks can be added here and any number 
        // of tasks can be assigned to a particular device.
        Stopwatch timer = new Stopwatch();
        timer.Start();
        System.Threading.Tasks.Task[] tasks = new Task[3]
        {
          Task.Factory.StartNew(() => MatrixMultiply(deviceGPU0, A, B)),
          Task.Factory.StartNew(() => MatrixMultiply(deviceGPU1, A, B)),
          Task.Factory.StartNew(() => MatrixMultiply(deviceCPU, A, B)),
        };

        // Block until all tasks complete
        Task.WaitAll( tasks );
        timer.Stop();
        Console.WriteLine( "Finished all double precision matrix multiplications in parallel in " + timer.ElapsedMilliseconds + " ms.\n" );

        // Dump the log file for verification.
        Console.WriteLine( writer );

        // Quit logging
        BridgeManager.Instance.DisableLogging();
      
      }
    }

    private static void MatrixMultiply( IComputeDevice device, DoubleMatrix A, DoubleMatrix B )
    {
      // Place this thread to the given compute device.
      BridgeManager.Instance.SetComputeDevice( device );

      Stopwatch timer = new Stopwatch();
      timer.Start();

      // Do this task work.
      NMathFunctions.Product( A, B );

      timer.Stop();
      Console.WriteLine( "Finished matrix multiplication on the " + device.DeviceName  + " in " + timer.ElapsedMilliseconds + " ms.\n" );
    }
    
</pre>
<pre lang="csharp">

</pre>
<p>The post <a rel="nofollow" href="https://www.centerspace.net/tasks-on-gpu">Distributing Parallel Tasks on Multiple GPU&#8217;s</a> appeared first on <a rel="nofollow" href="https://www.centerspace.net">CenterSpace</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://www.centerspace.net/tasks-on-gpu/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
		<post-id xmlns="com-wordpress:feed-additions:1">5397</post-id>	</item>
		<item>
		<title>An Introduction to Linear Algebra on the GPU</title>
		<link>https://www.centerspace.net/linear-algebra-gpu</link>
					<comments>https://www.centerspace.net/linear-algebra-gpu#respond</comments>
		
		<dc:creator><![CDATA[Paul Shirkey]]></dc:creator>
		<pubDate>Tue, 04 Jun 2013 19:02:38 +0000</pubDate>
				<category><![CDATA[NMath Premium]]></category>
		<category><![CDATA[C# GPU]]></category>
		<category><![CDATA[c# LAPACK GPU]]></category>
		<category><![CDATA[c# linear algebra]]></category>
		<category><![CDATA[NMath GPU]]></category>
		<category><![CDATA[NVIDIA GPU]]></category>
		<guid isPermaLink="false">http://www.centerspace.net/blog/?p=4383</guid>

					<description><![CDATA[<p><img src="https://www.centerspace.net/blog/wp-content/uploads/2013/05/nvidia_logo.gif" alt="" title="Nvida Logo" width="150" height="150" class="excerpt" /><br />
<strong>NMath Premium</strong> was designed to provide an easy to follow pathway for .NET developers to leverage the performance of the GPU without having to wade through the complexities of GPU programming and their attendant details.  And to provide a GPU-aware math library that can be used by developers to build once &#038; run anywhere without concerning themselves of their user's installed GPU model, version, or even the existence of an GPU.</p>
<p>The post <a rel="nofollow" href="https://www.centerspace.net/linear-algebra-gpu">An Introduction to Linear Algebra on the GPU</a> appeared first on <a rel="nofollow" href="https://www.centerspace.net">CenterSpace</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p><strong>NMath Premium</strong> was designed to provide an easy-to-follow path for .NET developers to leverage the performance of the GPU without having to wade through the complexities of GPU programming and their attendant details. <strong>NMath Premium</strong> allows developers to build once and run anywhere without concerning themselves with their users&#8217; installed GPU models and versions, or even the existence of a GPU. <strong>NMath Premium</strong> is designed with fail-safe CPU fallbacks based on problem size, installed GPU hardware, and configuration settings. <strong>NMath Premium</strong> supports a complete set of dense linear algebra operations that execute on a wide class NVIDIA GPU&#8217;s, all using the intuitive, easy-to-use <strong>NMath</strong> API. As a result, <strong>NMath Premium</strong> not only offers superior performance with GPU-enabled linear algebra functions but also leverages these GPU-enabled classes internally in a wide range of algorithms.</p>
<p><strong>NMath Premium</strong> will be released June 11, 2013. For immediate access, sign up <a href="https://www.centerspace.net/nmath-premium/">here</a> to join the beta program.</p>
<h2>An SVD example</h2>
<p>After installing and adding the <strong>NMath Premium</strong> assemblies to your project, the following example demonstrates the computation of a large SVD on the GPU. The <strong>NMath</strong> API has been largely preserved in <strong>NMath Premium</strong> so the following code example will be familiar to current <strong>NMath</strong> users as its syntax is identical to <strong>NMath</strong>. Nearly all <strong>NMath</strong> code will run correctly without edits and can be dropped into a <strong>NMath Premium</strong> project.</p>
<pre lang="csharp">   // Build a dense random float matrix
   var A = new FloatMatrix( 5000, 5000, new RandGenUniform( -1, 1, seed));

   // Build the SVD server and request the right vectors
   var server = new FloatSVDecompServer();
   server.ComputeLeftVectors = false;
   server.ComputeRightVectors = true;
   server.ComputeFull = false;

   // Do the SVD
   FloatSVDecomp svd = server.GetDecomp( A );</pre>
<p>Running in a <strong>NMath Premium</strong> project this <code>5000x5000</code> SVD decomposition can execute either on the GPU and CPU depending on the installed hardware and configuration settings, so most new users will want to immediately verify that their decomposition did indeed run on the GPU. To accomplish this <strong>NMath Premium</strong> provides a logging feature that allows programmers track where their GPU-aware classes routed their computation. The line of code below enables the logging feature &#8211; but because of the associated file writes logging should only be used while debugging and avoided in production code.</p>
<pre lang="csharp">#if DEBUG
   NMathConfiguration.EnableGPULogging = true;
#endif</pre>
<p>The log file will be written to a file named <code>NMathGPULapack.log</code> located next to the built executable. The location and name of this log file can be modified with the <code>NMathConfiguration</code> configuration class. The <code>NMathConfiguration</code> contains a number of new features and is worth a <a href="https://www.centerspace.net/doc/NMathSuite/ref/html/T_CenterSpace_NMath_Core_NMathConfiguration.htm" target="_blank">perusal</a>. It&#8217;s important to note that in the current release <em>the logging must be configured before any computational operations take place </em> otherwise an exception will be thrown. Logging cannot currently be turn on or off once <strong>NMath Premium</strong> has loaded it&#8217;s dependent <code>dlls</code> and started running computational algorithms.</p>
<p>Having run the simple example above, I see the following in my <code>NMathGPULapack</code> log file.</p>
<pre lang="basic">  cula info:  sgesvd (N, S, 5000, 5000, ... , 5000)
  cula info:  issuing to CPU (work query)
  cula info:  CPU library is lapackcpu.dll
  cula info:  work query returned 654872
  cula info:  done
  cula info:  sgesvd (N, S, 5000, 5000, ... , 5000)
  cula info:  issuing to GPU (over threshold)
  cula info:  done</pre>
<p>The first five lines record a query to the LAPACK library to determine the total memory requirements for this operation. This is simply a work query and does not run on the GPU. The final three lines record the operation name (<code>sgesvd</code>), size, where it ran and why. In this case the <code>5000x5000</code> SVD ran on the GPU because its size was over the cross-over threshold.</p>
<h2>Performance</h2>
<p>The <em>raison d&#8217;être</em> of GPU computation is performance and new users need to be aware of the various factors that impact GPU performance. For GPU developers leveraging a product like <strong>NMath Premium</strong> the three most important factors that determined the performance of a particular algorithm are:</p>
<ol>
<li>Installed GPU hardware</li>
<li>Size of problem</li>
<li>Computational precision, <code>Single</code> or <code>Double</code></li>
</ol>
<p>There are many other reasons that a particular algorithm will run well on a GPU including its computational complexity or how well it can be bent to run on highly parallel GPU architecture, but the three reasons above are paramount to our library users. Following the example above, if you happen to have run the SVD on an early model GeForce laptop GPU, the performance may not have been much better than running it in a CPU bound manner; although doing so would have freed your CPU for other tasks &#8211; an important collateral benefit of GPU computation. Likewise computational precision can have a major impact on GPU performance, and recognizing the single-precision graphics origin of GPU architecture, it&#8217;s important to match the required computational precision with the proper NVIDIA hardware, particularly if double precision is needed. Lastly, problem size is the primary determinate used by <strong>NMath Premium</strong> to route problems between the CPU and GPU; Because there is memory-transfer overhead involved in transferring data to the GPU, small problems are retained on the CPU and large problems are shifted to the GPU. This optimal routing can be controlled by the developer if fine control is needed, however most developers will use <strong>NMath Premium</strong> in its default configuration with great success.</p>
<p>-Happy Computing,</p>
<p>Paul Shirkey</p>
<p>The post <a rel="nofollow" href="https://www.centerspace.net/linear-algebra-gpu">An Introduction to Linear Algebra on the GPU</a> appeared first on <a rel="nofollow" href="https://www.centerspace.net">CenterSpace</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://www.centerspace.net/linear-algebra-gpu/feed</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
		<post-id xmlns="com-wordpress:feed-additions:1">4383</post-id>	</item>
	</channel>
</rss>
