Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix remaining C++ issues of Lcalc (also to let it build with clang) #12437

Closed
ohanar opened this issue Feb 4, 2012 · 52 comments
Closed

Fix remaining C++ issues of Lcalc (also to let it build with clang) #12437

ohanar opened this issue Feb 4, 2012 · 52 comments

Comments

@ohanar
Copy link
Member

ohanar commented Feb 4, 2012

Lcalc still uses some non-standard "features" of g++.

C++ compilers that are pickier than g++ will not allow this.

GCC 5.x again got stricter and now also needs the second "default parameter" patch (or once again -fpermissive) mentioned below.


Current branch fix usage of internal headers and some declarations. More to be done as I haven't even scratched the issues mentioned in this ticket - unless they have been fixed by another merged ticket.

CC: @kiwifb @SnarkBoojum @tscrim

Component: packages: standard

Keywords: C++11 C++14 GCC 5 clang

Author: François Bissey

Branch/Commit: f498bff

Reviewer: Travis Scrimshaw

Issue created by migration from https://trac.sagemath.org/ticket/12437

@ohanar
Copy link
Member Author

ohanar commented Feb 4, 2012

Attachment: lcalc-defaults.patch.gz

for review purposes

@ohanar

This comment has been minimized.

@nexttime
Copy link
Mannequin

nexttime mannequin commented Mar 22, 2012

Dependencies: #12681

@nexttime
Copy link
Mannequin

nexttime mannequin commented Mar 22, 2012

comment:3

We now need a new spkg (based on that of #12681) incorporating this patch.

We also should report this upstream.

Patch so far looks good (not sure whether I've seen all of it -- maybe trac truncated it); seems like most functions (also) had the default values in their declarations.

@nexttime nexttime mannequin added s: needs work and removed s: needs review labels Mar 22, 2012
@nexttime
Copy link
Mannequin

nexttime mannequin commented Mar 22, 2012

Work Issues: Create a new spkg.

@jdemeyer jdemeyer modified the milestones: sage-5.11, sage-5.12 Aug 13, 2013
@sagetrac-vbraun-spam sagetrac-vbraun-spam mannequin modified the milestones: sage-6.1, sage-6.2 Jan 30, 2014
@nexttime
Copy link
Mannequin

nexttime mannequin commented Apr 21, 2014

comment:8

GCC 4.9 now also requires -fpermissive to build Lcalc as well as the Cython extension modules that use Lcalc's headers, unless we fix Lcalc.

@nexttime
Copy link
Mannequin

nexttime mannequin commented Apr 21, 2014

comment:9

I'll check [laterTM] whether Andrew's patch still applies (and whether it is sufficient for GCC 4.9 at least).

@nexttime
Copy link
Mannequin

nexttime mannequin commented Apr 21, 2014

comment:10

Hmmm, haven't tested Andrew's patch [yet], but tried by myself.

For GCC 4.9, apparently the following tiny patch is sufficient to build Lcalc and the Sage library extension module (which currently lacks a depends btw.*):

diff -Naur lcalc-1.23-vanilla/include/Ldirichlet_series.h lcalc-1.23-fixed-gcc.4.9/include/Ldirichlet_series.h
--- lcalc-1.23-vanilla/include/Ldirichlet_series.h	2012-08-08 23:21:55.000000000 +0200
+++ lcalc-1.23-fixed-gcc.4.9/include/Ldirichlet_series.h	2014-04-21 14:37:59.027464849 +0200
@@ -43,7 +43,7 @@
  //XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
 template <class ttype>
 Complex L_function <ttype>::
-dirichlet_series(Complex s, long long N=-1)
+dirichlet_series(Complex s, long long N)
 {
     Complex z=0.;
     long long m,n;
diff -Naur lcalc-1.23-vanilla/include/L.h lcalc-1.23-fixed-gcc.4.9/include/L.h
--- lcalc-1.23-vanilla/include/L.h	2012-08-08 23:21:55.000000000 +0200
+++ lcalc-1.23-fixed-gcc.4.9/include/L.h	2014-04-21 14:32:04.003467348 +0200
@@ -491,7 +491,7 @@
 
     //#include "Ldirichlet_series.h" //for computing Dirichlet series
     Complex partial_dirichlet_series(Complex s, long long N1, long long N2);
-    Complex dirichlet_series(Complex s, long long N);
+    Complex dirichlet_series(Complex s, long long N=-1LL);
 
     //#include "Ltaylor_series.h" //for computing taylor series for Dirichlet series
     //void compute_taylor_series(int N, int K, Complex s_0, Complex *series);

(In addition to the patches to Lcalc we already have in Sage, of which only a trivial one is needed to build Lcalc outside of Sage.)


*

diff --git a/src/module_list.py b/src/module_list.py
index fa460be..b5449be 100755
--- a/src/module_list.py
+++ b/src/module_list.py
@@ -700,10 +700,12 @@ ext_modules = [
 
     Extension('sage.libs.lcalc.lcalc_Lfunction',
               sources = ['sage/libs/lcalc/lcalc_Lfunction.pyx'],
-              libraries = ['m', 'ntl', 'mpfr', 'gmp', 'gmpxx',
+              libraries = ['m', 'ntl', 'mpfr', 'gmp', 'gmpxx',         # XXX Are all of these really needed? (NTL??)
                            'Lfunction'],
               include_dirs = [SAGE_INC + "/libLfunction"],
-              extra_compile_args=["-O3", "-ffast-math"],
+              depends = [ os.path.join(SAGE_INC, "libLfunction", header)
+                          for header in ["L.h"] ],                     # maybe more headers from there
+              extra_compile_args=["-O3", "-ffast-math"],               # probably add '-Wno-deprecated', as of Lcalc 1.23
               language = 'c++'),
 
 

(And, despite having language="c++", the extension module is compiled with the C compiler, not the C++ compiler, such that -- besides other effects -- CXXFLAGS aren't used. It gets linked with g++ though.)

@ohanar
Copy link
Member Author

ohanar commented Apr 21, 2014

comment:11

Your patch looks like a subset of mine. I can't remember why I did all the things that I did in my patch, but I would guess that I needed them to compile with clang. It may be that gcc 4.9 is still too permissive in this case.

@nexttime
Copy link
Mannequin

nexttime mannequin commented Apr 21, 2014

comment:13

Replying to @ohanar:

Your patch looks like a subset of mine.

Yes. My primary goal was to make Lcalc work with GCC; I'll take a closer look at other changes later.

Adding void to the friend declaration of reset() is certainly correct (although slightly unrelated to what the name of the patch suggests, on the broader topic of this ticket, namely making Lcalc's code build with clang).

In the other hunks, you just removed default parameters from definitions, but did not move them to corresponding declarations (probably because there aren't any, which is something I'll have to check). But from at least one comment, it looks like those parts were "dead" code anyway.

@sagetrac-vbraun-spam sagetrac-vbraun-spam mannequin modified the milestones: sage-6.2, sage-6.3 May 6, 2014
@nexttime
Copy link
Mannequin

nexttime mannequin commented May 19, 2014

comment:15

Ok, so I've now created 7 new patches to fix all remaining clang/non-GNU/C++11 issues with Lcalc (except for some deprecation warnings):

Makefile_2-dont_compile_C_with_CXXFLAGS.patch
lcalc-1.23-fix_VLA_1.patch
lcalc-1.23-fix_VLA_2.patch
lcalc-1.23-fix_control_reaches_end_of_non-void_fn.patch
lcalc-1.23-fix_typeof.patch
lcalc-1.23-missing_return_type.patch
lcalc-1.23_default_parameters_2.patch

But I'd prefer to put them on a single ticket, i.e., to either open a new one, or repurpose one of the two existing ones. (But before doing so, I'll anyway polish them a bit, and probably merge some of them into another or into one of the existing ones.)

I did take a slightly different approach to variable-length arrays; instead of using std::vector<>, I'm using foo_t *_foo = new foo_t[dim1*dim2*dim3], along with a macro foo(i,j,k) which maps the indices to a single one, and of course added delete [] _foo where necessary.

So far tested with GCC 4.4, 4.8 and 4.9, clang 3.4.1, and a couple of -std=... variations.

@tobihan
Copy link

tobihan commented May 20, 2014

comment:16

Hi leif,

these are quite some patches. Do you plan to send them upstream?

@nexttime
Copy link
Mannequin

nexttime mannequin commented May 21, 2014

comment:17

Replying to @tobihan:

Hi leif,

these are quite some patches. Do you plan to send them upstream?

Well, upstream... ;-)

The patches are pretty small, and I'll merge them into fewer I think, hopefully next weekend.

Pretty a while ago, someoneTM wanted to create an autotools project for Michael, but that apparently never happened, so we keep heavily patching the existing Makefile.

AFAIK, some previous patches (e.g. dealing with newer PARI versions) went upstream, i.e., Michael should at least be aware of them; I'll certainly send him the new / updated ones later. Not sure whether he's interested in changes removing GNU extensions. (Variable-length arrays can still be used depending on macros / the compiler though.)

@tobihan
Copy link

tobihan commented May 21, 2014

comment:18

Well I hope upstreaming them works out. Sage is not the only downstream who needs these patches. There's at least Debian (where I'm maintaining the package) and Fedora. Having them upstream would make everyones live a lot easier.

@kiwifb

This comment has been minimized.

@kiwifb
Copy link
Member

kiwifb commented Sep 18, 2016

Author: François Bissey

@kiwifb kiwifb modified the milestones: sage-6.7, sage-7.5 Sep 18, 2016
@kiwifb
Copy link
Member

kiwifb commented Sep 18, 2016

comment:35

Next issue

[lcalc-1.23.p14] clang++ -O3   -ffast-math -fPIC   -I../include -c Lriemannsiegel.cc
[lcalc-1.23.p14] In file included from Lriemannsiegel.cc:24:
[lcalc-1.23.p14] In file included from ../include/L.h:539:
[lcalc-1.23.p14] ../include/Ldokchitser.h:72:14: error: variable length array of non-POD element type 'Complex' (aka 'complex<double>')
[lcalc-1.23.p14]     Complex m[N+1];
[lcalc-1.23.p14]              ^
[lcalc-1.23.p14] ../include/Ldokchitser.h:81:23: error: variable length array of non-POD element type 'Complex' (aka 'complex<double>')
[lcalc-1.23.p14]         Complex sum_log_Gamma[N+1][MYDIGITS+1];
[lcalc-1.23.p14]                              ^
[lcalc-1.23.p14] ../include/Ldokchitser.h:106:27: error: variable length array of non-POD element type 'Complex' (aka 'complex<double>')
[lcalc-1.23.p14]         Complex exp_sum_log_Gamma[N+1][MYDIGITS+1][MYDIGITS+1]; // symmetric functions
[lcalc-1.23.p14]                                  ^
[lcalc-1.23.p14] ../include/Ldokchitser.h:107:15: error: variable length array of non-POD element type 'Complex' (aka 'complex<double>')
[lcalc-1.23.p14]         Complex gamma[N+1][MYDIGITS+1]; // gamma(s+m[j]) for j = 1 to N
[lcalc-1.23.p14]                      ^
[lcalc-1.23.p14] In file included from Lriemannsiegel.cc:24:
[lcalc-1.23.p14] In file included from ../include/L.h:542:
[lcalc-1.23.p14] ../include/Lexplicit_formula.h:28:12: error: variable length array of non-POD element type 'Complex' (aka 'complex<double>')
[lcalc-1.23.p14]   Complex b[num_coeffs+1];
[lcalc-1.23.p14]            ^
[lcalc-1.23.p14] 5 errors generated.

@jdemeyer

This comment has been minimized.

@jdemeyer
Copy link

Changed dependencies from #12681, #18316 to none

@kiwifb
Copy link
Member

kiwifb commented Sep 29, 2016

comment:39

The issue I hit now with this is pretty much the VLA. I am guessing I can get the first VLA patch from #12436 but not the second one.

@nexttime do you still have those patches and can you share them?

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Sep 30, 2016

Branch pushed to git repo; I updated commit sha1. New commits:

f498bffAdapt old patch from Andrew Ohana for VLA in C++

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Sep 30, 2016

Changed commit from 8a9fe64 to f498bff

@kiwifb
Copy link
Member

kiwifb commented Sep 30, 2016

comment:41

Actually doing the VLA like Andrew did initially in #12436 is good enough. And while we have warnings for all the other stuff mentioned in this tickets it all compiled successfully with clang (latest on Sierra, based on 3.8).

@kiwifb kiwifb modified the milestones: sage-7.5, sage-7.4 Sep 30, 2016
@tscrim
Copy link
Collaborator

tscrim commented Oct 4, 2016

comment:42

I'm hesitant about the changes of the form:

+diff --git a/include/Ldokchitser.h b/include/Ldokchitser.h
+index c67f01a..7b3e5c9 100644
+--- a/include/Ldokchitser.h
++++ b/include/Ldokchitser.h
+@@ -69,7 +69,7 @@ phi_series(int precision)
+     
+     // compute the values m[j] for the respective lambda_k[j]
+     
+-    Complex m[N+1];
++    std::vector<Complex> m(N+1);
+     for (j=1;j<=N;j++)
+     	m[j] = -2*lambda_k[j] + 2;
+ 	

because my understanding is g++ to treats Complex m[N+1] as Complex *m = new Complex[N+1], which changing to std::vector could have an impact on performance. I haven't looked at the code itself, but my guess is that lcalc wanted to treat these as fixed length arrays whose size is determined at runtime.

@kiwifb
Copy link
Member

kiwifb commented Oct 4, 2016

comment:43

Correct, they are VLA. The replacement with new works very well for one dimensional arrays. Multidimensional ones are another story, I guess it would be similar with more ugly loops. It seems to me that the accepted behavior in C++ is to use vector for these (from stack overflow examples).
The mystery to me is that there are many more VLA in that particular code but only a few of them raise a flag. What gives?

@tscrim
Copy link
Collaborator

tscrim commented Oct 4, 2016

comment:44

I can understand why std::vector would be a natural choice because you don't have to worry about memory management (specifically the deallocation). It just there is some slight overhead from using it rather than direct system calls with the array, but that is more likely a micro-optimization. Perhaps some of the others aren't raising warnings because their length can be determined at compile time?

One little change to a patch:

         std::vector<std::vector<std::vector<Complex> > > exp_sum_log_Gamma(N+1); // symmetric functions
         std::vector<std::vector<Complex> > gamma(N+1); // gamma(s+m[j]) for j = 1 to N
         for (j=1;j<=N;j++){
             exp_sum_log_Gamma[j].resize(MYDIGITS+1);
+            for (n=0;n<=MYDIGITS;n++) exp_sum_log_Gamma[j][n].resize(MYDIGITS+1);
             gamma[j].resize(MYDIGITS+1);
         }
-        for (j=1;j<=N;j++) for (n=0;n<=MYDIGITS;n++) exp_sum_log_Gamma[j][n].resize(MYDIGITS+1);

as I think it is (slightly) more readable considering we are already working with the 3d array.

@kiwifb
Copy link
Member

kiwifb commented Oct 5, 2016

comment:45

I wouldn't worry too much about optimization at this stage. The compiler does a better job than you'll ever do on that. The only thing the compiler cannot do is find a better algorithm (although it may be able able to re-order your loops in a way you wouldn't have thought of).
For the little change I copied the structure of the original patch which does that in separate stages. If you feel it is clearer your way, feel free to commit your change as a part of your review (I can do it myself if you insist).

@tscrim
Copy link
Collaborator

tscrim commented Oct 5, 2016

Reviewer: Travis Scrimshaw

@tscrim
Copy link
Collaborator

tscrim commented Oct 5, 2016

Changed work issues from Locate patches and upload them... ;-) to none

@tscrim
Copy link
Collaborator

tscrim commented Oct 5, 2016

comment:46

It's in the realm of bikeshedding, so I'm sending this off to the buildbots.

@vbraun
Copy link
Member

vbraun commented Oct 21, 2016

Changed branch from u/fbissey/lcalc_clang to f498bff

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

6 participants