#include "config.h"
#include <stdlib.h>
#include <assert.h>
#include <string.h>
#include "libgfortran.h"
void
__unpack1 (const gfc_array_char * ret, const gfc_array_char * vector,
const gfc_array_l4 * mask, const gfc_array_char * field)
{
index_type rstride[GFC_MAX_DIMENSIONS];
index_type rstride0;
char *rptr;
index_type vstride0;
char *vptr;
index_type fstride[GFC_MAX_DIMENSIONS];
index_type fstride0;
const char *fptr;
index_type mstride[GFC_MAX_DIMENSIONS];
index_type mstride0;
const GFC_LOGICAL_4 *mptr;
index_type count[GFC_MAX_DIMENSIONS];
index_type extent[GFC_MAX_DIMENSIONS];
index_type n;
index_type dim;
index_type size;
index_type fsize;
size = GFC_DESCRIPTOR_SIZE (ret);
fsize = GFC_DESCRIPTOR_SIZE (field);
dim = GFC_DESCRIPTOR_RANK (ret);
for (n = 0; n < dim; n++)
{
count[n] = 0;
extent[n] = ret->dim[n].ubound + 1 - ret->dim[n].lbound;
rstride[n] = ret->dim[n].stride * size;
fstride[n] = field->dim[n].stride * fsize;
mstride[n] = mask->dim[n].stride;
}
if (rstride[0] == 0)
rstride[0] = size;
if (fstride[0] == 0)
fstride[0] = fsize;
if (mstride[0] == 0)
mstride[0] = 1;
vstride0 = vector->dim[0].stride * size;
if (vstride0 == 0)
vstride0 = size;
rstride0 = rstride[0];
fstride0 = fstride[0];
mstride0 = mstride[0];
rptr = ret->data;
fptr = field->data;
mptr = mask->data;
vptr = vector->data;
if (GFC_DESCRIPTOR_SIZE (mask) != 4)
{
if (GFC_DESCRIPTOR_SIZE (mask) != 8)
runtime_error ("Funny sized logical array");
for (n = 0; n < dim; n++)
mstride[n] <<= 1;
mstride0 <<= 1;
mptr = GFOR_POINTER_L8_TO_L4 (mptr);
}
while (rptr)
{
if (*mptr)
{
memcpy (rptr, vptr, size);
vptr += vstride0;
}
else
{
memcpy (rptr, fptr, size);
}
rptr += rstride0;
fptr += fstride0;
mptr += mstride0;
count[0]++;
n = 0;
while (count[n] == extent[n])
{
count[n] = 0;
rptr -= rstride[n] * extent[n];
fptr -= fstride[n] * extent[n];
mptr -= mstride[n] * extent[n];
n++;
if (n >= dim)
{
rptr = NULL;
break;
}
else
{
count[n]++;
rptr += rstride[n];
fptr += fstride[n];
mptr += mstride[n];
}
}
}
}
void
__unpack0 (const gfc_array_char * ret, const gfc_array_char * vector,
const gfc_array_l4 * mask, char * field)
{
gfc_array_char tmp;
tmp.dtype = 0;
tmp.data = field;
__unpack1 (ret, vector, mask, &tmp);
}