tiling_2d.c 4.87 KB
Newer Older
Swann Perarnau's avatar
Swann Perarnau committed
1 2 3 4 5 6 7 8 9 10
/*******************************************************************************
 * Copyright 2019 UChicago Argonne, LLC.
 * (c.f. AUTHORS, LICENSE)
 *
 * This file is part of the AML project.
 * For more info, see https://xgitlab.cels.anl.gov/argo/aml
 *
 * SPDX-License-Identifier: BSD-3-Clause
*******************************************************************************/

11
#include "aml.h"
12
#include "aml/tiling/2d.h"
13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60
#include <assert.h>

/*******************************************************************************
 * 2D Iterator
 ******************************************************************************/

int aml_tiling_iterator_2d_reset(struct aml_tiling_iterator_data *data)
{
	struct aml_tiling_iterator_2d_data *it =
		(struct aml_tiling_iterator_2d_data *)data;
	it->i = 0;
	return 0;
}

int aml_tiling_iterator_2d_end(const struct aml_tiling_iterator_data *data)
{
	const struct aml_tiling_iterator_2d_data *it =
		(const struct aml_tiling_iterator_2d_data *)data;
	return it->i * it->tiling->blocksize >= it->tiling->totalsize;
}

int aml_tiling_iterator_2d_next(struct aml_tiling_iterator_data *data)
{
	struct aml_tiling_iterator_2d_data *it =
		(struct aml_tiling_iterator_2d_data *)data;
	it->i++;
	return 0;
}

int aml_tiling_iterator_2d_get(const struct aml_tiling_iterator_data *data,
			       va_list args)
{
	const struct aml_tiling_iterator_2d_data *it =
		(const struct aml_tiling_iterator_2d_data *)data;
	unsigned long *x = va_arg(args, unsigned long *);
	*x = it->i;
	return 0;
}

struct aml_tiling_iterator_ops aml_tiling_iterator_2d_ops = {
	aml_tiling_iterator_2d_reset,
	aml_tiling_iterator_2d_next,
	aml_tiling_iterator_2d_end,
	aml_tiling_iterator_2d_get,
};

/*******************************************************************************
 * 2D ops
61
 * Tileids are the order in memory of the tiles.
62 63
 ******************************************************************************/

64
int aml_tiling_2d_rowmajor_tileid(const struct aml_tiling_data *t, va_list ap)
65 66 67
{
	const struct aml_tiling_2d_data *data =
		(const struct aml_tiling_2d_data *)t;
68 69 70 71 72 73
	size_t row = va_arg(ap, size_t);
	size_t col = va_arg(ap, size_t);
	if(row >= data->ndims[0] || col >= data->ndims[1])
		return -1;
	else
		return (row*data->ndims[1]) + col;
74 75
}

76
int aml_tiling_2d_colmajor_tileid(const struct aml_tiling_data *t, va_list ap)
77 78 79
{
	const struct aml_tiling_2d_data *data =
		(const struct aml_tiling_2d_data *)t;
80 81 82 83
	size_t row = va_arg(ap, size_t);
	size_t col = va_arg(ap, size_t);
	if(row >= data->ndims[0] || col >= data->ndims[1])
		return -1;
84
	else
85
		return (col*data->ndims[0]) + row;
86 87
}

88 89 90 91 92 93 94 95 96 97 98 99
size_t aml_tiling_2d_tilesize(const struct aml_tiling_data *t, int tileid)
{
	const struct aml_tiling_2d_data *data =
		(const struct aml_tiling_2d_data *)t;
	if(tileid < 0 || tileid >= data->ndims[0]*data->ndims[1])
		return 0;
	else
		return data->blocksize;
}

void* aml_tiling_2d_tilestart(const struct aml_tiling_data *t,
			      const void *ptr, int tileid)
100 101 102 103
{
	const struct aml_tiling_2d_data *data =
		(const struct aml_tiling_2d_data *)t;
	intptr_t p = (intptr_t)ptr;
104
	if(tileid < 0 || tileid >= data->ndims[0]*data->ndims[1])
105 106
		return NULL;
	else
107
		return (void *)(p + tileid*data->blocksize);
108 109 110 111 112 113
}

int aml_tiling_2d_ndims(const struct aml_tiling_data *t, va_list ap)
{
	const struct aml_tiling_2d_data *data =
		(const struct aml_tiling_2d_data *)t;
114 115
	size_t *nrows = va_arg(ap, size_t *);
	size_t *ncols = va_arg(ap, size_t *);
116
	/* looks totally wrong */
117 118
	*nrows = data->ndims[0];
	*ncols = data->ndims[1];
119 120 121 122 123 124 125
	return 0;
}

int aml_tiling_2d_init_iterator(struct aml_tiling_data *t,
				struct aml_tiling_iterator *it, int flags)
{
	assert(it->data != NULL);
126
	struct aml_tiling_iterator_2d_data *data =
127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157
		(struct aml_tiling_iterator_2d_data *)it->data;
	it->ops = &aml_tiling_iterator_2d_ops;
	data->i = 0;
	data->tiling = (struct aml_tiling_2d_data *)t;
	return 0;
}

int aml_tiling_2d_create_iterator(struct aml_tiling_data *t,
				  struct aml_tiling_iterator **it, int flags)
{
	intptr_t baseptr, dataptr;
	struct aml_tiling_iterator *ret;
	baseptr = (intptr_t) calloc(1, AML_TILING_ITERATOR_2D_ALLOCSIZE);
	dataptr = baseptr + sizeof(struct aml_tiling_iterator);

	ret = (struct aml_tiling_iterator *)baseptr;
	ret->data = (struct aml_tiling_iterator_data *)dataptr;

	aml_tiling_2d_init_iterator(t, ret, flags);
	*it = ret;
	return 0;
}


int aml_tiling_2d_destroy_iterator(struct aml_tiling_data *t,
				   struct aml_tiling_iterator *it)
{
	return 0;
}


158 159 160 161
struct aml_tiling_ops aml_tiling_2d_rowmajor_ops = {
	aml_tiling_2d_create_iterator,
	aml_tiling_2d_init_iterator,
	aml_tiling_2d_destroy_iterator,
162
	aml_tiling_2d_rowmajor_tileid,
163
	aml_tiling_2d_tilesize,
164
	aml_tiling_2d_tilestart,
165 166 167 168
	aml_tiling_2d_ndims,
};

struct aml_tiling_ops aml_tiling_2d_colmajor_ops = {
169 170 171
	aml_tiling_2d_create_iterator,
	aml_tiling_2d_init_iterator,
	aml_tiling_2d_destroy_iterator,
172
	aml_tiling_2d_colmajor_tileid,
173
	aml_tiling_2d_tilesize,
174
	aml_tiling_2d_tilestart,
175
	aml_tiling_2d_ndims,
176
};