This is a read only copy of the old FEniCS QA forum. Please visit the new QA forum to ask questions

Coefficient rank error: wrong C++ or UFL?

+1 vote

EDIT: removed everything now, still an error

Dear all,

I have the usual simple linear elastic problem, and now I'd like to have a vector of expressions and detection classes to specify arbitrary Neumann conditions. In order to do that, I'm using vectors of shared pointers, but somewhere I'm doing bad things.

You can find a minimal example here.

The error is this:

*** -------------------------------------------------------------------------
*** Error:   Unable to assemble form.
*** Reason:  Invalid value rank for coefficient 0 (got 0 but expecting 1). You might have forgotten to specify the value rank correctly in an Expression subclass.
*** Where:   This error was encountered inside AssemblerBase.cpp.
*** Process: unknown
*** 
*** DOLFIN version: 1.5.0
*** Git changeset:  f467b66dcfd821ec20e9f9070c7cef5a991dbc42
*** -------------------------------------------------------------------------

I've removed everything from the UFL, now it's this:

# Bilinear form
a = inner(u, v) * dx #inner(sigma(u), eps(v))*dx

# Known term
L = inner(f, v) * dx #+ inner(f1, v) * ds(1) + inner(f2, v) * ds(2) + inner(f3, v) * ds(3) + inner(f4, v) * ds(4) + inner(f5, v) * ds(5)

# Export
forms = [a, L]

The only coefficient now is f, which is assigned as follows:

// Bulk force
rhs.f = dolfin::Constant(0.0, 0.0);

When assembling the matrix, I get the exception:

// Assign RHS markers
rhs.ds = boundary_markers;

// Numerical system
dolfin::PETScMatrix A;
dolfin::PETScVector b;

// Assemble
dolfin::assemble_system(A, b, lhs, rhs, bcs); // <---- BOOM

I am missing something stupid probably...

Thanks for any pointers!

asked Mar 14, 2016 by senseiwa FEniCS User (2,620 points)
edited Mar 16, 2016 by senseiwa

I have edited the question.

In my code I've removed everything from the UFL, I am not using any subclass now, just a plain Coefficient, and I still get the error.

I have no ideas...

Another point. I decided to print all the coefficients, and I get an error because there are no coefficients:

auto v = lhs.coefficients();
std::cout << "COUNT IS " << v.size() << std::endl;
std::cout << "NAME  IS " << lhs.coefficient_name(0) << std::endl;

*** Error:   Unable to access coefficient data.
*** Reason:  There are no coefficients.

Now I'm puzzled. Why then I have this error?

*** Reason:  Invalid value rank for coefficient 0 (got 0 but expecting 1). You might have forgotten to specify the value rank correctly in an Expression subclass.

Hi, please provide us with a minimal example that produces the error. This is ideally a pair of files: UFL file with the form and a CPP file as a driver.

Thanks @MiroK, I have included a complete example code. I may have done something wrong somewhere else, although the probability is close to null, so all you have to see is the UFL file elasticity.ufl and the linear elastic problem elastic.cpp.

As I've read the answer by @gifo75, I can say that all you have to really care about is the elastic.cpp file.

Any hints would be useful...

I have narrowed down to these few lines, removes all possible pointers, without any hope to get it working:

auto V  = elasticity::Form_a::TestSpace(mesh_.object);

// Subspaces for BCs
dolfin::SubSpace V0(V, 0);
dolfin::SubSpace V1(V, 1);

// Dirichlet BCs
std::vector<const dolfin::DirichletBC*> bcs;

//
// DO EVERYTHING MANUALLY
//
bcs.push_back(new dolfin::DirichletBC(V,
                                      dolfin::Constant(0.0, 0.0),
                                      edgedetect(dolfin::Point(0.0, 0.0), dolfin::Point(7.0, 0.0), conf_)));
bcs.push_back(new dolfin::DirichletBC(V,
                                      dolfin::Constant(1.0, 16.0),
                                      edgedetect(dolfin::Point(0.0, 16.0), dolfin::Point(7.0, 16.0), conf_)));

// Bilinear and linear forms
elasticity::Form_a lhs(V, V);
elasticity::Form_L rhs(V);

// Bulk force
rhs.f = constantload(conf_.bulk[0], conf_.bulk[1]);;

// Numerical system
dolfin::PETScMatrix A;
dolfin::PETScVector b;

// Assemble
dolfin::assemble_system(A, b, lhs, rhs, bcs);

UFL

# Bilinear form
a = inner(u, v) * dx

# Known term
L = inner(f, v) * dx

2 Answers

0 votes
 
Best answer

This is unusual, to self-answer, but I have posted another question here, because something is missing.

The TL;DR answer: DO NOT USE TEMPORARIES, USE SHARED POINTERS

When creating a DirichletBC do not use a code that use temporary variables as this dolfin::Constant:

// Bad code
bcs.push_back(new dolfin::DirichletBC(*V,
                    dolfin::Constant(0.0, 0.0), // <---- CRASH
                    edgedetect(dolfin::Point(0.0, 0.0), dolfin::Point(7.0, 0.0))));

If you avoid this constructor, and use a shared pointer (or create a separate variable) then no crash will happen:

// Happy code
bcs.push_back(new dolfin::DirichletBC(V,
                                      std::make_shared<const dolfin::Constant>(0.0, 0.0),
                                      std::make_shared<const edgedetect>(dolfin::Point(0.0, 0.0), dolfin::Point(7.0, 0.0), conf_)));

Thank you.

answered Mar 21, 2016 by senseiwa FEniCS User (2,620 points)
+1 vote

Dear all,

I've played with the code and found a weird behavior. When using an assignment to the coefficient f, the error changes if I use a variable, or an inline:

    dolfin::Constant testing(1.0, 1.0);
    rhs.f = testing;

*** Error:   Unable to evaluate expression.
*** Reason:  Missing eval() function (must be overloaded).

INLINE

    rhs.f = dolfin::Constant(1.0, 1.0);

*** Error:   Unable to assemble form.
*** Reason:  Invalid value rank for coefficient 0 (got 0 
    but expecting 1). You might have forgotten to specify
    the value rank correctly in an Expression subclass.

Why is this?

Thanks!

answered Mar 16, 2016 by gifo75 FEniCS Novice (650 points)

Yes, I see the same here. Weird.

...