Skip to content

Commit

Permalink
Add trace operation
Browse files Browse the repository at this point in the history
  • Loading branch information
brucehow committed Sep 13, 2019
1 parent 10bda8c commit b6a1bd6
Show file tree
Hide file tree
Showing 5 changed files with 150 additions and 11 deletions.
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,6 @@

# Compiled files
matrix

# Resource files
resources/
80 changes: 71 additions & 9 deletions matrix.c
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,11 @@ int main(int argc, char *argv[]) {
bool log = false;
int arg = 1; // Argument pointer
int threads = -1;

// Timing variables
time_t t = time(NULL);
struct tm tm = *localtime(&t);
float load_time, routine_time;

// CLA processing
if (argc < 4) {
Expand Down Expand Up @@ -171,16 +174,16 @@ int main(int argc, char *argv[]) {
rows = read_mat_dim(fp);
cols = read_mat_dim(fp);
data = read_line(fp);
struct COO matrix = coo_format(rows, cols, type, data);
struct COO coo_matrix = coo_format(rows, cols, type, data);
end = clock();
float load_time = (double) (end - start) / CLOCKS_PER_SEC; // Divide by CPS for seconds
load_time = (double) (end - start) / CLOCKS_PER_SEC; // Divide by CPS for seconds

// Perform the scalar multiplication routine
start = clock();
scalar_multiply(matrix, routine.scalar);
scalar_multiply(coo_matrix, routine.scalar);
end = clock();
float routine_time = (double) (end - start) / CLOCKS_PER_SEC;
matrix.type = TYPE_FLOAT; // Float scalar results in float matrix
routine_time = (double) (end - start) / CLOCKS_PER_SEC;
coo_matrix.type = TYPE_FLOAT; // Float scalar results in float matrix

if (log) {
char *output_file = get_output_name(tm, "sm");
Expand All @@ -189,19 +192,78 @@ int main(int argc, char *argv[]) {
fprintf(stderr, "matrix: failed to generate output file\n");
exit(EXIT_FAILURE);
}
write_details(output, filename, filename2, rows, cols, routine.type, matrix.type);
write_coo_data(output, matrix);
write_details(output, filename, filename2, rows, cols, routine.type, coo_matrix.type);
write_coo_data(output, coo_matrix);
write_times(output, load_time, routine_time);
printf("matrix: successfully logged results to '%s'\n", output_file);
fclose(output);
free(output_file);
} else {
write_details(stdout, filename, filename2, rows, cols, routine.type, matrix.type);
write_coo_data(stdout, matrix);
write_details(stdout, filename, filename2, rows, cols, routine.type, coo_matrix.type);
write_coo_data(stdout, coo_matrix);
write_times(stdout, load_time, routine_time);
}
break;
case TR:
// Read input file
start = clock();
type = read_mat_type(fp);
rows = read_mat_dim(fp);
cols = read_mat_dim(fp);
if (rows != cols) {
fprintf(stderr, "matrix: the trace routine can only be performed on square matrices\n");
exit(EXIT_FAILURE);
}
data = read_line(fp);
struct CSR csr_matrix = csr_format(rows, cols, type, data);
end = clock();
load_time = (double) (end - start) / CLOCKS_PER_SEC; // Divide by CPS for seconds

// Perform the trace routine
union {
int i;
float f;
} trace_result;
if (csr_matrix.type == TYPE_INT) {
start = clock();
trace_result.i = trace(csr_matrix);
end = clock();
routine_time = (double) (end - start) / CLOCKS_PER_SEC;
} else {
start = clock();
trace_result.f = trace_f(csr_matrix);
end = clock();
routine_time = (double) (end - start) / CLOCKS_PER_SEC;
}

if (log) {
char *output_file = get_output_name(tm, "tr");
FILE *output = fopen(output_file, "w"); // sample file
if(output == NULL) {
fprintf(stderr, "matrix: failed to generate output file\n");
exit(EXIT_FAILURE);
}
write_details(output, filename, filename2, rows, cols, routine.type, csr_matrix.type);

// Write single trace value
if (csr_matrix.type == TYPE_INT) {
fprintf(output, "%d\n", trace_result.i);
} else {
fprintf(output, "%f\n", trace_result.f);
}
write_times(output, load_time, routine_time);
printf("matrix: successfully logged results to '%s'\n", output_file);
fclose(output);
free(output_file);
} else {
write_details(stdout, filename, filename2, rows, cols, routine.type, csr_matrix.type);
if (csr_matrix.type == TYPE_INT) {
fprintf(stdout, "%d\n", trace_result.i);
} else {
fprintf(stdout, "%f\n", trace_result.f);
}
write_times(stdout, load_time, routine_time);
}
break;
case AD:
break;
Expand Down
31 changes: 31 additions & 0 deletions matrix.h
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,10 @@ extern struct CSC csc_format(int rows, int cols, enum VAR_TYPE type, char *data)
*/
extern void scalar_multiply(struct COO matrix, float scalar);

extern int trace(struct CSR matrix);

extern float trace_f(struct CSR matrix);

/**
* Allocates memory of a given size using malloc
*
Expand Down Expand Up @@ -136,10 +140,37 @@ void *reallocate(void *ptr, size_t size);
*/
extern char *get_output_name(struct tm tm, char *routine);

/**
* Writes the time taken to process and load data and the time taken
* to execute the specified algebraic routine
*
* @param fp The file pointer to output to
* @param load_time The process and load time in seconds
* @param routine_time The algebraic routine execution time in seconds
*/
extern void write_times(FILE *fp, float load_time, float routine_time);

/**
* Writes the COO structure data to the given file pointer.
* The function assumes that the x,y values for each element
* is sorted to take advantage of quicker printing algorithms
*
* @param fp The file pointer to output to
* @param matrix The matrix containing the data to write from
*/
extern void write_coo_data(FILE *fp, struct COO matrix);

/**
* Writes the header details to the given file pointer
*
* @param fp The file pointer to output to
* @param filename The filename of the first matrix
* @param filename2 The filename of the second matrix if any
* @param rows The number of rows in the matrix
* @param cols The number of columns in the matrix
* @param routine The algebraic routine type
* @param type The variable type of the matrix
*/
extern void write_details(FILE *fp, char* filename, char* filename2, int rows, int cols, enum ROUTINE_TYPE routine, enum VAR_TYPE type);

// COO representation
Expand Down
1 change: 1 addition & 0 deletions output.c
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,7 @@ void write_coo_data(FILE *fp, struct COO matrix) {
if (matrix.type == TYPE_INT) {
for (int i = 0; i < matrix.rows; i++) {
for (int j = 0; j < matrix.cols; j++) {
// Assuming elements x,y are sorted
if (matrix.elements[pos].x != i) { // Skip checking elements if none are on the same row
fprintf(fp, "0");
count += matrix.cols - j;
Expand Down
46 changes: 44 additions & 2 deletions routines.c
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,50 @@ void scalar_multiply(struct COO matrix, float scalar) {
}
}

void trace(struct COO matrix) {

int trace(struct CSR matrix) {
int trace = 0;

for (int i = 1; i < matrix.rows + 1; i++) {
// Check num of elements in row i
int elements = matrix.ia[i] - matrix.ia[i-1];
if (elements == 0) {
continue;
}
int pos = matrix.ia[i-1]; // Starting index for ja/nnz
while (pos - matrix.ia[i-1] <= elements) {
if (matrix.ja[pos] == i - 1) {
trace += matrix.nnz.i[pos];
break;
} else if (matrix.ja[pos] > i - 1) {
break;
}
pos++;
}
}
return trace;
}

float trace_f(struct CSR matrix) {
float trace = 0.0;

for (int i = 1; i < matrix.rows + 1; i++) {
// Check num of elements in row i
int elements = matrix.ia[i] - matrix.ia[i-1];
if (elements == 0) {
continue;
}
int pos = matrix.ia[i-1]; // Starting index for ja/nnz
while (pos - matrix.ia[i-1] <= elements) {
if (matrix.ja[pos] == i - 1) {
trace += matrix.nnz.f[pos];
break;
} else if (matrix.ja[pos] > i - 1) {
break;
}
pos++;
}
}
return trace;
}

void transpose(struct COO matrix) {
Expand Down

0 comments on commit b6a1bd6

Please sign in to comment.