Skip to content

LAPACKE_sgesdd_work on armv7 android float-abi=hard never returns for some cases #894

Closed
@Mikaso

Description

@Mikaso

Hi!

I'm using openblas on an android device. So far everything works fine, but now I'm facing a strange error. In my function, I'm calling LAPACKE_sgesdd_work directly using preallocated memory.

For special cases: It never returns.

I compiled LAPACKE_sgesdd_work with debug flags and jumped into the disassembly: It runs until it gets into the fortran call sgesdd_. It never returns from there.

This code should give you the same behavior on an armv7 device:

float A[ 9 ] = {  1.f,  0.f, -1.f,
                 -2.f,  1.f,  4.f,
                 -3.f,  4.f,  5.f };

float U[ 9 ]; float S[ 3 ]; float V_t[ 9 ];

/* number of rows of A */
const int m = 3;
/* number of cols of A */
const int n = 3;
/* leading dimension of A */
const int ld_a = n;
/* leading dimension of U */
const int ld_u = m;
/* leading dimension of V_t */
const int ld_v_t = n;
/* SVD workspace array */
int iwork[ 8 * 4 ];
/* SVD workspace array length */
int lwork = 180;
/* SVD workspace array */
float work[ 180 * 2 ];

int result = 1;

result = LAPACKE_sgesdd_work(LAPACK_ROW_MAJOR, 'A', m, n, A, ld_a, S, U, ld_u,
                                                     V_t, ld_v_t, work, lwork, iwork);

Crucial: If I compile exactly the same code for x86, it works.

I do allocate more memory than needed just to be sure that there is no access vialoation inside.

On the other hand the following does work:

float A[ 4 ] = {  1.f,  0.f,
                 -2.f,  1.f };

float U[ 4 ]; float S[ 2 ]; float V_t[ 4 ];

/* number of rows of A */
const int m = 2;
/* number of cols of A */
const int n = 2;
/* leading dimension of A */
const int ld_a = n;
/* leading dimension of U */
const int ld_u = m;
/* leading dimension of V_t */
const int ld_v_t = n;
/* SVD workspace array */
int iwork[ 8 * 3 ];
/* SVD workspace array length */
int lwork = LAPACK_GESDD_LWORK( 3, 3 );
/* SVD workspace array */
float work[ LAPACK_GESDD_LWORK( 3, 3 ) ];

int result = 1;

result = LAPACKE_sgesdd_work(LAPACK_ROW_MAJOR, 'A', m, n, A, ld_a, S, U, ld_u,
                                                     V_t, ld_v_t, work, lwork, iwork);

I can now even confirm, it is the same behavior when calling sgesdd_ directly:

 float A[ 9 ] = {  1.f,  0.f, -1.f,
                  -2.f,  1.f,  4.f,
                  -3.f,  4.f,  5.f };

float U[ 9 ]; float S[ 3 ]; float V_t[ 9 ];

/* number of rows of A */
int m = 3;
/* number of cols of A */
int n = 3;
/* leading dimension of A */
int ld_a = n;
/* leading dimension of U */
int ld_u = m;
/* leading dimension of V_t */
int ld_v_t = n;
/* SVD workspace array */
int iwork[ 8 * 4 ];
/* SVD workspace array length */
int lwork = 180;
/* SVD workspace array */
float work[ 180 * 2 ];

char jobz = 'A';
int info = 1;

sgesdd_(&jobz, &m, &n, A, &ld_a, S, U, &ld_u, V_t,
        &ld_v_t, work, &lwork, iwork, &info );

I also tested the latter example with lapack-3.6.0 using reference BLAS from netlib and there it works.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions