I assume here that you are referring to working with the Eigen3 c++ library. This is not clear from your question. if not, you should consider it. In any case, within Eigen, there is no need to actually copy the triangular part, to get a selfadjoint matrix. Eigen has the concept of views, and you can use a self adjoint view in order to perform an operation like e.g.
using namespace Eigen;
MatrixXd m(m,n);
...
(generate uppper triangular entries in m)
...
VectorXd r(n), p(n);
r = m.selfadjointView<Upper>() * p;
here is a small example to illustrate using fixed size matrices:
#include <Eigen/Core>
using namespace std;
using namespace Eigen;
int main()
{
Matrix2d m,c;
m << 1, 2,
0, 1;
Vector2d x(0,2), r;
// perform copy operation
c = m.selfadjointView<Upper>();
cout << c << endl;
// directly apply selfadjoint view in matrix operation
// (no entries are copied)
r = m.selfadjointView<Upper>() * x;
}
the output will be
[1, 2,
2, 1].
now, the result in r
is the same as if you had used c * x
instead. Just that there is no need for copying the values in the original matrix to make it selfadjoint.