\documentclass[a4paper,12pt]{article}
\usepackage{amsmath}
\usepackage{amssymb}
\usepackage[polish]{babel}
\usepackage{polski}
\usepackage[utf8]{inputenc}
\usepackage{indentfirst}
\usepackage{geometry}
\usepackage{array}
\usepackage[pdftex]{color,graphicx}
\usepackage{subfigure}
\usepackage{afterpage}
\usepackage{setspace}
\usepackage{color}
\usepackage{wrapfig}
\usepackage{listings}
\usepackage{datetime}

\renewcommand{\onehalfspacing}{\setstretch{1.6}}

\geometry{tmargin=2.5cm,bmargin=2.5cm,lmargin=2.5cm,rmargin=2.5cm}
\setlength{\parindent}{1cm}
\setlength{\parskip}{0mm}

\newenvironment{lista}{
\begin{itemize}
  \setlength{\itemsep}{1pt}
  \setlength{\parskip}{0pt}
  \setlength{\parsep}{0pt}
}{\end{itemize}}

\newcommand{\linia}{\rule{\linewidth}{0.4mm}}

\definecolor{lbcolor}{rgb}{0.95,0.95,0.95}
\lstset{
    backgroundcolor=\color{lbcolor},
    tabsize=4,
  language=C++,
  captionpos=b,
  tabsize=3,
  frame=lines,
  numbers=left,
  numberstyle=\tiny,
  numbersep=5pt,
  breaklines=true,
  showstringspaces=false,
  basicstyle=\footnotesize,
  identifierstyle=\color{magenta},
  keywordstyle=\color[rgb]{0,0,1},
  commentstyle=\color{Darkgreen},
  stringstyle=\color{red}
  }

\begin{document}

\noindent
\begin{tabular}{|c|p{11cm}|c|} \hline 
Grupa 1 & Piotr Dergun, Dominik Waśko & \ddmmyyyydate\today \tabularnewline
\hline 
\end{tabular}


\section*{Zadanie 3 - Mnożenie macierzy GPU}

Celem zadania jest obliczenie iloczynu dwóch macierzy prostokątnych  o wymiarach n x n, wykorzystując karte graficzną oraz technologię CUDA . Posługując się zapisem matematycznym zadanie można zapisać jako równanie: A*B = C. 
Kerlen odpowiadający za mnożenie macierzy wygląda następująco:
\begin{lstlisting}
__global__ void multiply(char *a,char *b,int *c, int N){
	int i =blockIdx.x * blockDim.x + threadIdx.x;
	int sum = 0;
	int temp,temp2;
	while(i<N*N){
		temp = (int)floor((float)(i/N*N));
		temp2 = i%N;
		for(int j=0;j<N;j++){
			sum +=a[temp + j] * b[j*N + temp2 ];
		}
		c[i]=sum;
		sum =0;
		i+=blockDim.x * gridDim.x;
	}
}	
\end{lstlisting}

Najpierw obliczany jest indeks 'i' tablicy 'c' dla którego ten wątek ma zacząć obliczenia. Gdy watek obliczy już sumę z i-tego wiersza macierzy A oraz i-tej kolumny macierzy B następuje inkrementacja zmiennej 'i' o całkowitą ilość uruchomionych wątków (czyli ilość bloków * ilość wątków). Dzięki temu w możliwe jest obliczenie wszystkich komórek tablicy C nawet w sytuacji gdy ilość wątków jest mniejsza od ilość komórek tablicy C.   

Wypełnianie macierzy A i B losowymi wartościami również odbywa się na karcie graficznej. Algorytm jest bardzo podobny do tego obliczającego iloczyn macierzy. 

Zadanie zostało uruchomione na komputerze wyposażonym w karte graficzna NVIDIA GeForce GT 640M. Karta posiada dwa multiprocesory po 192 rdzenie CUDA, taktowane zegarem 709 MHz. Pamięć karty to 980MB. 

Program testowano na tablicy o rozmiarze 2048x2048. Parametry dla jakich uruchomiono program to 3 rozmiary siatki: 16, 64, 256 oraz dla każdego rozmiaru siatki rozmiar bloku: 64,128,192,256,512,1024.

Na rysunku 1. przedstawiono wykres zależności czasu obliczeń od rozmiaru bloku dla wszystkich trzech rozmiarów siatki. Można  zauważyć, że  czas obliczeń najbardziej spada przy zwiększeniu rozmiaru bloku do 192. Dalsze zwiększanie rozmiaru bloku nie powoduje ciągłego zwiększania szybkości, czas obliczeń utrzymuje się równym poziomie. Rozmiar siatki ma bardzo mały wpływ na szybkość obliczeń.  





\begin{figure}[h]
\includegraphics[width=1.1\textwidth]{wykres.png}
\caption{Wykres czasu obliczeń od rozmiaru bloku.}
\label{fig:figure2}
\end{figure}




\end{document}
