From ae2ecc64f1af8a2a28c756376e84df20a1a96a02 Mon Sep 17 00:00:00 2001 From: bmusuko <bram.musuko@gmail.com> Date: Sat, 28 Mar 2020 18:29:23 +0700 Subject: [PATCH] init cuda file --- djikstra_cuda.cu | 144 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 144 insertions(+) create mode 100644 djikstra_cuda.cu diff --git a/djikstra_cuda.cu b/djikstra_cuda.cu new file mode 100644 index 0000000..e4b0a24 --- /dev/null +++ b/djikstra_cuda.cu @@ -0,0 +1,144 @@ +#include <stdio.h> +#include <stdlib.h> +#include <limits.h> +#include <stdbool.h> +#include <sys/time.h> +#include <string.h> +// #include <cuda.h> + +#define INFINITY INT_MAX; +#define MIN(a,b) (((a)<(b))?(a):(b)); +#define MAX(a,b) (((a)>(b))?(a):(b)); + +void createGraph(int n, int graph[n]){ + srand(13517032); + int val; + for(int i=0;i<n;i++){ + graph[i*n+i] = 0; + for(int j=i+1;j<n;j++){ + val = (rand() % 50) + 1; + graph[i*n+j] = val; + graph[j*n+i] = val; + } + } +} + +void printGraph(int n, int graph[n]){ + for(int i=0;i<n;i++){ + for(int j=0;j<n;j++){ + printf("%d ",graph[i*n+j]); + } + printf("\n"); + } + printf("\n"); +} + +__device__ +void djikstra(int graph[],int start,int distance[],int visited[],int n,int answer[]){ + + int node; + int temp_dist; + int min_dist[2]; // node and its distance + min_dist[0] = -1; + min_dist[1] = INFINITY; + for(int i = 0;i<n;i++){ + if(i == start){ + visited[i] = true; + distance[i] = 0; + } else{ + visited[i] = false; + distance[i] = graph[start*n+i]; + if(distance[i] < min_dist[1]){ + min_dist[1] = distance[i]; + min_dist[0] = i; + } + } + } + + // initialized distance with a + for(int i = 0;i<n+1;i++){ + node = min_dist[0]; + visited[node] = true; + distance[node] = min_dist[1]; + min_dist[0] = -1; + min_dist[1] = INFINITY; + for (int j=0;j<n;j++){ + if(visited[j] == 0){ + temp_dist = MIN(distance[node] + graph[node*n+j],distance[j]); + if(temp_dist < min_dist[1]){ + min_dist[0] = j; + min_dist[1] = temp_dist; + } + if(distance[j] > temp_dist){ + distance[j] = temp_dist; + } + } + + } + } + for(int i=0;i<n;i++){ + answer[start*n+i] = distance[i]; + + } +} + +__global__ +void djikstra_cuda(int graph[]int distance[],int visited[],int n,int answer[]) +{ + int index = blockIdx.x * blockDim.x + threadIdx.x; + int stride = blockDim.x * gridDim.x; + for (int i = index; i < n; i += stride){ + djikstra(graph,i,distance,visited[],n,answer); + } +} + +int main(int argc, char** argv){ + + if (argc != 2){ + printf("Invalid argument\n./djikstra <number_of_node>\n"); + return 0; + } + FILE* output_file; + + struct timeval st, et; + int n = atoi(argv[1]); + + char filename[80]; + strcpy(filename, "output_"); + strcat(filename, argv[1]); + strcat(filename,".txt"); + output_file = fopen(filename, "w+"); + + int *graph,*distance,*visited, *answer; + graph = malloc(n*n*sizeof(int)); + distance = malloc(n*sizeof(int)); + visited = malloc(n*sizeof(int)); + answer = malloc(n*n*sizeof(int)); + createGraph(n,graph); + fprintf(output_file, "GRAPH:\n"); + for(int i = 0;i<n;i++){ + for(int j = 0;j<n;j++){ + fprintf(output_file, "%d ", graph[i*n+j]); + } + fprintf(output_file, "\n"); + } + fprintf(output_file, "\n\n\n"); + + int blockSize = 256; + int numBlocks = (n + blockSize - 1) / blockSize; + + gettimeofday(&st,NULL); + djikstra_cuda<<<numBlocks, blockSize>>>>(graph,distance,visited,n,answer); + gettimeofday(&et,NULL); + unsigned long long int elapsed = ((et.tv_sec - st.tv_sec) * 1000000) + (et.tv_usec - st.tv_usec); + printf("Djikstra total time: %llu micro seconds\n",elapsed); + fprintf(output_file, "Answer:\n"); + for(int i = 0;i<n;i++){ + for(int j = 0;j<n;j++){ + fprintf(output_file, "%d ", answer[i*n+j]); + } + fprintf(output_file, "\n"); + } + return 0; +} + -- GitLab