     printf("time: iteration.\n");
     printCudaTimer(&timerIteration);
     resetCudaTimer(&timerIteration);
+
+    cudaMemset(graphSwing, 0, sizeof(float));
+    cudaMemset(graphTract, 0, sizeof(float));
+
+    // Run reductions on vertex swing and traction.
+    startCudaTimer(&timer);
+    fa2GraphSwingTract<<<numblocks_reduction, BLOCK_SIZE>>>(
+        g->numvertices,
+        swg, tra, numNeighbours,
+        graphSwing, graphTract);
+    stopCudaTimer(&timer);
+    printf("time: graph swing and traction.\n");
+    printCudaTimer(&timer);
+    resetCudaTimer(&timer);
+
+    code = cudaGetLastError();
+    if (code != cudaSuccess)
+    {
+      printf("Error in kernel 1.\n%s\n", cudaGetErrorString(code));
+      exit(EXIT_FAILURE);
+    }
+
+    fa2MoveVertices<<<numblocks, BLOCK_SIZE>>>(
+        vxLocs,
+        vyLocs,
+        g->numvertices,
+        tra,
+        swg,
+        forceX,
+        forceY,
+        oldForceX,
+        oldForceY,
+        graphSwing,
+        graphTract);
   }
 
   startCudaTimer(&timerMem2);

    unsigned int numedges,
    unsigned int* numNeighbours,
    float* tra, float* swg, 
    float* oldForceX, float* oldForceY,
    float* graphSwing,
    float* graphTract,


  if (gid < numvertices)
  {
    if (gid == 0)
    {
      *graphSwing = 0.0;
      *graphTract = 0.0;
    }

    forceX[gid] = 0;
    forceY[gid] = 0;

    // Gravity force
    fa2Gravity(gid, numvertices, vxLocs, vyLocs, &forceX[gid], &forceY[gid], numNeighbours);
    // Repulsion between vertices
    fa2Repulsion(gid, numvertices, vxLocs, vyLocs, &forceX[gid], &forceY[gid], numNeighbours);
    // Attraction on edges
    fa2Attraction(gid, numvertices, vxLocs, vyLocs, numedges, edgeSources,
        edgeTargets, &forceX[gid], &forceY[gid]);

    // Calculate speed of vertices.
    // Update swing of vertices.
    fa2UpdateSwing(gid, numvertices, forceX[gid], forceY[gid], oldForceX, oldForceY, swg);

    // Update traction of vertices.
    fa2UpdateTract(gid, numvertices, forceX[gid], forceY[gid], oldForceX, oldForceY, tra);
  }
}

__global__ void fa2MoveVertices(
    float* vxLocs, float* vyLocs,
    unsigned int numvertices,
    float* tra, float* swg,
    float* forceX, float* forceY,
    float* oldForceX, float* oldForceY,
    float* graphSwing,
    float* graphTract)
{
  unsigned int gid = threadIdx.x + (blockIdx.x * BLOCK_SIZE);

  if (gid < numvertices)
  {
    float speed = 0;
    float dispX = 0;
    float dispY = 0;

    float graphSpeed = 0;

    // Update speed of Graph.
    fa2UpdateSpeedGraph(*graphSwing, *graphTract, &graphSpeed);

    // Update speed of vertices.
    fa2UpdateSpeed(gid, numvertices, &speed, swg, forceX[gid], forceY[gid], graphSpeed);

    // Update displacement of vertices.
    fa2UpdateDisplacement(gid, numvertices, speed, forceX[gid], forceY[gid], &dispX, &dispY);

    // Update vertex locations based on speed.
    fa2UpdateLocation(gid, numvertices, vxLocs, vyLocs, dispX, dispY);

    // Set current forces as old forces in vertex data.
    fa2SaveOldForces(gid, numvertices, forceX[gid], forceY[gid], oldForceX, oldForceY);
  }
}

