* which compiler is right (either to compile or to barf)... @ 2022-12-01 4:51 leon zadorin 2022-12-01 9:35 ` LIU Hao 0 siblings, 1 reply; 13+ messages in thread From: leon zadorin @ 2022-12-01 4:51 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 1022 bytes --] Hi everyone, I would be interested to hear the opinions of C++ standard experts on which compiler is correctly dealing with the below code (GCC 12.2 -std=c++20 compiles fine, MSVC19.33 /std:c++20 compiles fine, Clang 15.0.0 -std=c++20 barfs) #include <memory> #include <vector> #include <optional> struct X; template <typename T> struct J { typedef typename T::x aoeu; }; struct S { ::std::vector<::std::shared_ptr<J<X>>> v; }; static ::std::optional<S> opt; struct X { typedef int x; }; int main () { } Clang barfs with: incomplete type 'X' named in nested name specifier typedef typename T::x aoeu Interestingly if S::v is not a vector, i.e. instead of ::std::vector<::std::shared_ptr<J<X>>> v; v is just ::std::shared_ptr<J<X>> v; ... then clang compiles fine. Also, if optional is replaced with say unique_ptr, clang also builds fine. I would be interested in being educated on the standard (of which I am not a lawyer :) ) what would be the correctly mandated behavior? Kind regards Leon. ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-01 4:51 which compiler is right (either to compile or to barf) leon zadorin @ 2022-12-01 9:35 ` LIU Hao 2022-12-01 23:26 ` leon zadorin 0 siblings, 1 reply; 13+ messages in thread From: LIU Hao @ 2022-12-01 9:35 UTC (permalink / raw) To: leon zadorin, gcc-help [-- Attachment #1.1: Type: text/plain, Size: 541 bytes --] 在 2022/12/1 12:51, leon zadorin via Gcc-help 写道: > Hi everyone, > > I would be interested to hear the opinions of C++ standard experts on which > compiler is correctly dealing with the below code (GCC 12.2 -std=c++20 > compiles fine, MSVC19.33 /std:c++20 compiles fine, Clang 15.0.0 -std=c++20 > barfs) > I think this is a bug in Clang. Instantiation of `shared_ptr<T<U>>` is not meant to instantiate `T<U>`. Your code actually compiles fine if the definition of `J` was not provided. -- Best regards, LIU Hao [-- Attachment #2: OpenPGP digital signature --] [-- Type: application/pgp-signature, Size: 840 bytes --] ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-01 9:35 ` LIU Hao @ 2022-12-01 23:26 ` leon zadorin 2022-12-01 23:54 ` Jonathan Wakely 0 siblings, 1 reply; 13+ messages in thread From: leon zadorin @ 2022-12-01 23:26 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 2159 bytes --] On Thu, Dec 1, 2022 at 8:35 PM LIU Hao <lh_mouse@126.com> wrote: > > I think this is a bug in Clang. Instantiation of `shared_ptr<T<U>>` is not > meant to instantiate > `T<U>`. Your code actually compiles fine if the definition of `J` was not > provided. > > -- > Best regards, > LIU Hao > Thanks :) It is rather interesting, there is a discussion at https://github.com/llvm/llvm-project/issues/59292 which may be pointing to implementation differences between stdlibc++ and libc++ etc. There is thinknig that it just may be UB in the originally-posted code (if so then clang is rather helpful there, but only when used with libstdc++ apparently.. as I haven't personally verified the delta between building against different libs :) :) ) The current thought prorcess is that std component must be allowed by the standard to be instantiated with incomplete type T. And vector is allowed so indeed (but I think it must be complete by the time its members, e.g. via member-function invocation, are referenced)... so then it may come down to std::optional and its implementation -- whether its ctor is referencing any vector's members (dtor etc.) ... I suppose the official way would be to find whether ::std::optional may be instantiated with incomplete type T (say even if only when using default, no value present, ctor overload)... and if it not mentioned of being able to do so then it would be a bug in the original code (at which point having some toolchain being able to detect it is rather super nice :) :) I dont know to be honest if standard's doco for such ctor , e.g. constexpr optional() noexcept; constexpr optional(nullopt_t) noexcept; Postconditions: *this does not contain a value. <https://timsong-cpp.github.io/cppwp/n4861/optional#ctor-1.sentence-1> Remarks: No contained value is initialized. <https://timsong-cpp.github.io/cppwp/n4861/optional#ctor-2.sentence-1> For every object type T these constructors are constexpr constructors would be sufficient to infer the ability to instantiate with incomplete type... probably not (I'm not enough of an expert to see through this with my cloudy head atm :) ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-01 23:26 ` leon zadorin @ 2022-12-01 23:54 ` Jonathan Wakely 2022-12-01 23:56 ` Jonathan Wakely 2022-12-02 0:17 ` leon zadorin 0 siblings, 2 replies; 13+ messages in thread From: Jonathan Wakely @ 2022-12-01 23:54 UTC (permalink / raw) To: leon zadorin; +Cc: gcc-help On Thu, 1 Dec 2022 at 23:27, leon zadorin via Gcc-help <gcc-help@gcc.gnu.org> wrote: > > On Thu, Dec 1, 2022 at 8:35 PM LIU Hao <lh_mouse@126.com> wrote: > > > > > I think this is a bug in Clang. Instantiation of `shared_ptr<T<U>>` is not > > meant to instantiate > > `T<U>`. Your code actually compiles fine if the definition of `J` was not > > provided. > > > > -- > > Best regards, > > LIU Hao > > > > Thanks :) It is rather interesting, there is a discussion at > https://github.com/llvm/llvm-project/issues/59292 > which may be pointing to implementation differences between stdlibc++ and > libc++ etc. > > There is thinknig that it just may be UB in the originally-posted code (if > so then clang is rather helpful there, but only when used with libstdc++ > apparently.. as I haven't personally verified the delta between building > against different libs :) :) ) > > The current thought prorcess is that std component must be allowed by the > standard to be instantiated with incomplete type T. And vector is allowed > so indeed (but I think it must be complete by the time its members, e.g. > via member-function invocation, are referenced)... so then it may come down > to std::optional and its implementation -- whether its ctor is referencing > any vector's members (dtor etc.) ... > > I suppose the official way would be to find whether ::std::optional may be > instantiated with incomplete type T It may not be. (say even if only when using default, > no value present, ctor overload)... and if it not mentioned of being able > to do so then it would be a bug in the original code (at which point having > some toolchain being able to detect it is rather super nice :) :) > > I dont know to be honest if standard's doco for such ctor , e.g. > constexpr optional() noexcept; constexpr optional(nullopt_t) noexcept; > Postconditions: *this does not contain a value. > <https://timsong-cpp.github.io/cppwp/n4861/optional#ctor-1.sentence-1> > Remarks: No contained value is initialized. > <https://timsong-cpp.github.io/cppwp/n4861/optional#ctor-2.sentence-1> > For every object type T these constructors are constexpr > constructors > > would be sufficient to infer the ability to instantiate with incomplete > type... probably not (I'm not enough of an expert to see through this with > my cloudy head atm :) Those constructors are irrelevant. It's undefined to instantiate *any* std::lib template with an incomplete type unless *explicitly* permitted. It is explicitly permitted for vector and shared_ptr. It is not permitted for optional. ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-01 23:54 ` Jonathan Wakely @ 2022-12-01 23:56 ` Jonathan Wakely 2022-12-02 0:17 ` leon zadorin 1 sibling, 0 replies; 13+ messages in thread From: Jonathan Wakely @ 2022-12-01 23:56 UTC (permalink / raw) To: leon zadorin; +Cc: gcc-help On Thu, 1 Dec 2022 at 23:54, Jonathan Wakely wrote: > Those constructors are irrelevant. It's undefined to instantiate *any* > std::lib template with an incomplete type unless *explicitly* > permitted. It is explicitly permitted for vector and shared_ptr. It is > not permitted for optional. I forgot to give the standard reference. See [res.on.functions] p2 (2.5). ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-01 23:54 ` Jonathan Wakely 2022-12-01 23:56 ` Jonathan Wakely @ 2022-12-02 0:17 ` leon zadorin 2022-12-02 6:37 ` LIU Hao 1 sibling, 1 reply; 13+ messages in thread From: leon zadorin @ 2022-12-02 0:17 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 2078 bytes --] On Fri, Dec 2, 2022 at 10:54 AM Jonathan Wakely <jwakely.gcc@gmail.com> wrote: > On Thu, 1 Dec 2022 at 23:27, leon zadorin via Gcc-help > <gcc-help@gcc.gnu.org> wrote: > > The current thought prorcess is that std component must be allowed by the > > standard to be instantiated with incomplete type T. And vector is allowed > > so indeed (but I think it must be complete by the time its members, e.g. > > via member-function invocation, are referenced)... so then it may come > down > > to std::optional and its implementation -- whether its ctor is > referencing > > any vector's members (dtor etc.) ... > > > > I suppose the official way would be to find whether ::std::optional may > be > > instantiated with incomplete type T > > It may not be. > > > (say even if only when using default, > > no value present, ctor overload)... and if it not mentioned of being able > > to do so then it would be a bug in the original code (at which point > having > > some toolchain being able to detect it is rather super nice :) :) > > > > I dont know to be honest if standard's doco for such ctor , e.g. > > constexpr optional() noexcept; constexpr optional(nullopt_t) noexcept; > > Postconditions: *this does not contain a value. > > <https://timsong-cpp.github.io/cppwp/n4861/optional#ctor-1.sentence-1> > > Remarks: No contained value is initialized. > > <https://timsong-cpp.github.io/cppwp/n4861/optional#ctor-2.sentence-1> > > For every object type T these constructors are constexpr > > constructors > > > > would be sufficient to infer the ability to instantiate with incomplete > > type... probably not (I'm not enough of an expert to see through this > with > > my cloudy head atm :) > > Those constructors are irrelevant. It's undefined to instantiate *any* > std::lib template with an incomplete type unless *explicitly* > permitted. It is explicitly permitted for vector and shared_ptr. It is > not permitted for optional. > Thanks Jonathan for clarifying, as always - very precise and helpful. I'll close the issue on the clang side also. ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-02 0:17 ` leon zadorin @ 2022-12-02 6:37 ` LIU Hao 2022-12-02 7:18 ` leon zadorin 0 siblings, 1 reply; 13+ messages in thread From: LIU Hao @ 2022-12-02 6:37 UTC (permalink / raw) To: leon zadorin, gcc-help [-- Attachment #1.1: Type: text/plain, Size: 1055 bytes --] 在 2022/12/2 08:17, leon zadorin via Gcc-help 写道: > Thanks Jonathan for clarifying, as always - very precise and helpful. I'll > close the issue on the clang side also. No, you do not _instantiate_ `J<X>`. The behavior would have been undefined if you did. `::std::shared_ptr<J<X>> p;` is fine on itself, because `J<X>` is not instantiated. On the other hand, `::std::shared_ptr<J<X>> p(static_cast<J<X>*>(nullptr));` is undefined, as it instantiates a delete expression. In addition to that, [temp.point]/1 specifies that the point of instantiation of members of a class template _follows the end of_ namespace scope of the most enclosing specialization. This allows use before definition, which is not permitted for non-template classes: std::shared_ptr<struct foo> ptr( (struct foo*) nullptr); // instantiates `delete (struct foo*) ___` struct foo { };\x0f // the line above would have undefined behavior without this So, either way, your code is not undefined. -- Best regards, LIU Hao [-- Attachment #2: OpenPGP digital signature --] [-- Type: application/pgp-signature, Size: 840 bytes --] ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-02 6:37 ` LIU Hao @ 2022-12-02 7:18 ` leon zadorin 2022-12-02 7:22 ` leon zadorin 2022-12-02 7:45 ` LIU Hao 0 siblings, 2 replies; 13+ messages in thread From: leon zadorin @ 2022-12-02 7:18 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 2464 bytes --] On Fri, Dec 2, 2022 at 5:37 PM LIU Hao <lh_mouse@126.com> wrote: > 在 2022/12/2 08:17, leon zadorin via Gcc-help 写道: > No, you do not _instantiate_ `J<X>`. The behavior would have been > undefined if you did. > `::std::shared_ptr<J<X>> p;` is fine on itself, because `J<X>` is not > instantiated. On the other > hand, `::std::shared_ptr<J<X>> p(static_cast<J<X>*>(nullptr));` is > undefined, as it instantiates a > delete expression. > > > In addition to that, [temp.point]/1 specifies that the point of > instantiation of members of a class > template _follows the end of_ namespace scope of the most enclosing > specialization. This allows use > before definition, which is not permitted for non-template classes: > > std::shared_ptr<struct foo> ptr( > (struct foo*) nullptr); // instantiates `delete (struct foo*) > ___` > > struct foo { }; // the line above would have undefined behavior > without this > > > So, either way, your code is not undefined. > > Wow, ok, many thanks -- veeery interesting :) So I'm getting confused a little :) Let me summarize here: (1) On the one hand, given that I do instantiate ::std::optional with S (whith has member v whose elements' types, I guess(?) are at the line of declaring 'static ::std::optional<S> s', are still incompletely denifed, i.e. X) -- the clang discussion appears to say that at this moment optional is instantiated and S is incomplete (?) ... as so it is a UB... which I understood Jonathan's comment to relate to as well. (2) However, from your comment it would appear that 'instantiation of members of class template' is done afterwards anyways... I suppose to reconcile both bits of info: (a) 'instantitation of members of class template' ... is it the same for instantitaion of the class template itself? (because UB specs appears to provide restrictions on std lib class instantiations, not specifically to inner members, but just for whole class)?; and (b) in the above code right at the line 'static ::std::optional<S> s' is S considered incomplete type at that moment? ... I'm just trying to figure out whether template "::std::optional<S>" is, itself, being instantiated at that very line (never mind its members) and if type S at that moment is considered to be incomplete... in which case it is UB... if not then may be its not a UB... I am confused :) ha ha :) wouldn't be the first time though :) ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-02 7:18 ` leon zadorin @ 2022-12-02 7:22 ` leon zadorin 2022-12-02 7:45 ` LIU Hao 1 sibling, 0 replies; 13+ messages in thread From: leon zadorin @ 2022-12-02 7:22 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 2754 bytes --] On Fri, Dec 2, 2022 at 6:18 PM leon zadorin <leonleon77@gmail.com> wrote: > On Fri, Dec 2, 2022 at 5:37 PM LIU Hao <lh_mouse@126.com> wrote: > >> 在 2022/12/2 08:17, leon zadorin via Gcc-help 写道: >> No, you do not _instantiate_ `J<X>`. The behavior would have been >> undefined if you did. >> `::std::shared_ptr<J<X>> p;` is fine on itself, because `J<X>` is not >> instantiated. On the other >> hand, `::std::shared_ptr<J<X>> p(static_cast<J<X>*>(nullptr));` is >> undefined, as it instantiates a >> delete expression. >> >> >> In addition to that, [temp.point]/1 specifies that the point of >> instantiation of members of a class >> template _follows the end of_ namespace scope of the most enclosing >> specialization. This allows use >> before definition, which is not permitted for non-template classes: >> >> std::shared_ptr<struct foo> ptr( >> (struct foo*) nullptr); // instantiates `delete (struct foo*) >> ___` >> >> struct foo { }; // the line above would have undefined behavior >> without this >> >> >> So, either way, your code is not undefined. >> >> > Wow, ok, many thanks -- veeery interesting :) So I'm getting confused a > little :) > > Let me summarize here: > > (1) On the one hand, given that I do instantiate ::std::optional with S > (whith has member v whose elements' types, I guess(?) are at the line of > declaring 'static ::std::optional<S> s', are still incompletely denifed, > i.e. X) -- the clang discussion appears to say that at this moment optional > is instantiated and S is incomplete (?) ... as so it is a UB... which I > understood Jonathan's comment to relate to as well. > > (2) However, from your comment it would appear that 'instantiation of > members of class template' is done afterwards anyways... > > I suppose to reconcile both bits of info: > > (a) 'instantitation of members of class template' ... is it the same for > instantitaion of the class template itself? (because UB specs appears to > provide restrictions on std lib class instantiations, not specifically to > inner members, but just for whole class)?; and > > (b) in the above code right at the line 'static ::std::optional<S> s' is S > considered incomplete type at that moment? > > ... I'm just trying to figure out whether template "::std::optional<S>" > is, itself, being instantiated at that very line (never mind its members) > and if type S at that moment is considered to be incomplete... in which > case it is UB... if not then may be its not a UB... I am confused :) ha ha > :) wouldn't be the first time though :) > sorry in the above 'static ::std::optional<S> s' should read 'static ::std::optional<S> opt' of course -- a bloody typo :) ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-02 7:18 ` leon zadorin 2022-12-02 7:22 ` leon zadorin @ 2022-12-02 7:45 ` LIU Hao 2022-12-02 8:34 ` leon zadorin 1 sibling, 1 reply; 13+ messages in thread From: LIU Hao @ 2022-12-02 7:45 UTC (permalink / raw) To: leon zadorin, gcc-help [-- Attachment #1.1: Type: text/plain, Size: 2746 bytes --] 在 2022/12/2 15:18, leon zadorin via Gcc-help 写道: > (1) On the one hand, given that I do instantiate ::std::optional with S > (whith has member v whose elements' types, I guess(?) are at the line of > declaring 'static ::std::optional<S> s', are still incompletely denifed, > i.e. X) -- the clang discussion appears to say that at this moment optional > is instantiated and S is incomplete (?) ... as so it is a UB... which I > understood Jonathan's comment to relate to as well. > Yes this requires `S` to be complete. > (2) However, from your comment it would appear that 'instantiation of > members of class template' is done afterwards anyways... > Only `S` itself is required to be complete. In your code: struct S { ::std::vector<::std::shared_ptr<J<X>>> v; }; `S` _is_ complete. It does not matter whether it contains a `vector` of or a `shared_ptr` to incomplete types, because the standard allows so. ([vector.overview] 4, [util.smartptr.shared] 2) > I suppose to reconcile both bits of info: > > (a) 'instantitation of members of class template' ... is it the same for > instantitaion of the class template itself? (because UB specs appears to > provide restrictions on std lib class instantiations, not specifically to > inner members, but just for whole class)?; and > No. ``` struct T; extern T* eptr; // okay; pointer to incomplete type struct S { shared_ptr<T> mptr; // okay; `shared_ptr` to incomplete type }; void use_s() { S s; // oayk; `S` is complete s.mptr.reset(); // okay; `reset()` does not require `T` to // be complete s.mptr.reset(::eptr); // error; instantiates the default // deleter expression which requires // `T` to be complete } ``` > (b) in the above code right at the line 'static ::std::optional<S> s' is S > considered incomplete type at that moment? > No. See above. > ... I'm just trying to figure out whether template "::std::optional<S>" is, > itself, being instantiated at that very line (never mind its members) and > if type S at that moment is considered to be incomplete... in which case it > is UB... if not then may be its not a UB... I am confused :) ha ha :) > wouldn't be the first time though :) If `shared_ptr` is a bad example for you, here is a much simpler one: ``` struct incomplete; struct complete { incomplete* ptr; // okay incomplete& ref; // also okay incomplete val; // invalid use of incomplete type }; ``` -- Best regards, LIU Hao [-- Attachment #2: OpenPGP digital signature --] [-- Type: application/pgp-signature, Size: 840 bytes --] ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-02 7:45 ` LIU Hao @ 2022-12-02 8:34 ` leon zadorin 2022-12-02 9:16 ` leon zadorin 0 siblings, 1 reply; 13+ messages in thread From: leon zadorin @ 2022-12-02 8:34 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 1333 bytes --] On Fri, Dec 2, 2022 at 6:45 PM LIU Hao <lh_mouse@126.com> wrote: > 在 2022/12/2 15:18, leon zadorin via Gcc-help 写道: > > (1) On the one hand, given that I do instantiate ::std::optional with S > > (whith has member v whose elements' types, I guess(?) are at the line of > > declaring 'static ::std::optional<S> s', are still incompletely denifed, > > i.e. X) -- the clang discussion appears to say that at this moment > optional > > is instantiated and S is incomplete (?) ... as so it is a UB... which I > > understood Jonathan's comment to relate to as well. > > > > Yes this requires `S` to be complete. > ... > > Only `S` itself is required to be complete. > > > In your code: > > struct S { > ::std::vector<::std::shared_ptr<J<X>>> v; > }; > > `S` _is_ complete. It does not matter whether it contains a `vector` of or > a `shared_ptr` to > incomplete types, because the standard allows so. ([vector.overview] 4, > [util.smartptr.shared] 2) > ah..., ok -- thanks very much for explaining! If that is the case then indeed you are correct -- there is no UB it would seem (I had updated the comment in clang discussion https://github.com/llvm/llvm-project/issues/59292#issuecomment-1334898870 , hopefully they may re-open the issue then :) . Many thanks for clarifying :) ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-02 8:34 ` leon zadorin @ 2022-12-02 9:16 ` leon zadorin 2022-12-02 10:50 ` leon zadorin 0 siblings, 1 reply; 13+ messages in thread From: leon zadorin @ 2022-12-02 9:16 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 1227 bytes --] Sorry, just one more question :) So if we have static ::std::foo<S> f; and foo indeed considers S to be complete... is it then permitted to reference S's members and call S's member functions (like dtor()) in foo's constructor? I guess a silly consideration would be foo's constructor where it would create a temporary S and destroy it (for no specific reason other than to illustrate a point)... e.g. foo::foo() { S tmp; } now... if S type had a member of vector with incomplete type and standard allows for vector itself to be instantiated but not its members when T is incomplete as per vector.overview] 4) ... then at a time of '~S' (tmp being destructed) would not vector's destructor also be called? ... and at that point in time will it not reference the members of vector? Perhaps I am confusing myself with 'instantiation' of template types vs 'creation' of variables... at a time of 'static ::std::foo<S> f', i.e. the 'f' variable being actually created... the S.v (our vector of incomplete type) would already be instantiated/type-complete (as in: concrete type inferred from template processing)? Sorry for all the naive questions here -- haven't dived into this thinking for a while... getting old :) ^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: which compiler is right (either to compile or to barf)... 2022-12-02 9:16 ` leon zadorin @ 2022-12-02 10:50 ` leon zadorin 0 siblings, 0 replies; 13+ messages in thread From: leon zadorin @ 2022-12-02 10:50 UTC (permalink / raw) To: gcc-help [-- Attachment #1: Type: text/plain, Size: 311 bytes --] Ah! Light-bulb moment... I just got the whole 'Im not actually instantiating J<X>' bit... wow :) way to overcomplicate it in my own head by trying to, incompetently, read the standard wording... ha ha :) I think I get it now :) thanks and sorry for the noise in the last couple of posts :) Thanks Liu :) :) :) ^ permalink raw reply [flat|nested] 13+ messages in thread
end of thread, other threads:[~2022-12-02 10:50 UTC | newest] Thread overview: 13+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2022-12-01 4:51 which compiler is right (either to compile or to barf) leon zadorin 2022-12-01 9:35 ` LIU Hao 2022-12-01 23:26 ` leon zadorin 2022-12-01 23:54 ` Jonathan Wakely 2022-12-01 23:56 ` Jonathan Wakely 2022-12-02 0:17 ` leon zadorin 2022-12-02 6:37 ` LIU Hao 2022-12-02 7:18 ` leon zadorin 2022-12-02 7:22 ` leon zadorin 2022-12-02 7:45 ` LIU Hao 2022-12-02 8:34 ` leon zadorin 2022-12-02 9:16 ` leon zadorin 2022-12-02 10:50 ` leon zadorin
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).