- Is this safe? - 7 Updates
- Link at runtime instead of build-time - 4 Updates
- Found a use case for `const` by value return, a shared queue - 8 Updates
- Pass by rvalue reference - 4 Updates
- strange error (QT Creator 4.12.2, based on QT creator 5.14.2) - 1 Update
- reference to reference (Type &&) - 1 Update
Malcolm McLean <malcolm.arthur.mclean@gmail.com>: Mar 05 07:11AM -0800 On Saturday, 4 March 2023 at 22:55:37 UTC, Ben Bacarisse wrote: > would be a Malcolm function, and you can't mean all the bits in the > entire (virtual) system or the specification for such a function would > be ridiculous. A mathematical function doesn't cease to be a mathematical function because its specification is ridiculous. If each possible bit state on code entry maps to one and only one possible bit state on code exit, and the code doesn't do anything else, like turn LEDs on or off, then the code is a "function" or if you prefer, a "Malcolm function". |
Tim Rentsch <tr.17687@z991.linuxsc.com>: Mar 05 08:13AM -0800 > intents and purposes, the term is identical in meaning to the term > "function", used in the accepted sense in a computer context, not in > the C sense to mean "subroutine". This posting is not a response but a request for clarification. Is this function int contents_of( int *p ){ return *p; } one you would call a Malcolm function? |
Malcolm McLean <malcolm.arthur.mclean@gmail.com>: Mar 05 09:05AM -0800 On Sunday, 5 March 2023 at 16:14:15 UTC, Tim Rentsch wrote: > return *p; > } > one you would call a Malcolm function? Yes. On code entry, bits are pointed to by p. On code exit, the return value contains the same bits. It's not a very useful function, but it's clearly a function, in the mathematical sense of computing a mapping of one bit state to another bit state, and doing nothing else. You can argue that, on many architectures, if we pass it null, it will put a message on the error output stream, and terminate the program. A function can't do that. So it's not a function. But the answer is that invalid values of p are not in its domain, and it's still a function. I don't use the term "Malcolm function". They just functions (of bits). The confusion is because C uses the term to mean "subroutine", and other languages sometimes use the term syntactically, to mean code with a return values that can be uses as the right hand side of an assignment. But people have got the idea that the concept is my invention, whilst it isn't. It's very well established terminology. |
Ben Bacarisse <ben.usenet@bsb.me.uk>: Mar 05 08:44PM >> be ridiculous. > A mathematical function doesn't cease to be a mathematical function > because its specification is ridiculous. Of course. And the same would be true of non-mathematical functions as well. I'm trying to find out how your functions are specified. How is the Malcolm function that "just returns 10" specified? > possible bit state on code exit, and the code doesn't do anything > else, like turn LEDs on or off, then the code is a "function" or if > you prefer, a "Malcolm function". So int f(int x) { extern int inc; return x + inc++; } is a Malcolm function, yes? -- Ben. |
Mr Flibble <flibble2@reddwarf.jmc.corp>: Mar 05 09:00PM On 05/03/2023 20:44, Ben Bacarisse wrote: > So > int f(int x) { extern int inc; return x + inc++; } > is a Malcolm function, yes? Mathematical functions don't have side-effects; f has side effects so isn't a mathematical function. /Flibble |
"Chris M. Thomasson" <chris.m.thomasson.1@gmail.com>: Mar 05 01:59PM -0800 On 3/5/2023 1:00 PM, Mr Flibble wrote: >> is a Malcolm function, yes? > Mathematical functions don't have side-effects; f has side effects so > isn't a mathematical function. Imvvho, it is still "mathematical", in the sense that it performs mathematical "tasks" on the mutable state? A side effect to me means the function did something else besides providing a return value. |
Malcolm McLean <malcolm.arthur.mclean@gmail.com>: Mar 05 02:26PM -0800 On Sunday, 5 March 2023 at 20:44:59 UTC, Ben Bacarisse wrote: > Of course. And the same would be true of non-mathematical functions as > well. I'm trying to find out how your functions are specified. How is > the Malcolm function that "just returns 10" specified? It's embedded in the code somewhere. So for each possible (legal) state of the bit store on code entry there is one and one only state of the bit store on code exit, and the code does not cause any actions over than moving bits in the memory to be taken. So it's code that calculates a function, or a "Malcolm function". Of course you'd specify it as "returns 10". It's not particularly helpful to think in terms of the whole bit store. It's only helpful if you want to draw a distinction between code which calculates functions and code which performs actions, and someone is a bit shaky on what a function is. > So > int f(int x) { extern int inc; return x + inc++; } > is a Malcolm function, yes? Exactly. With this one, we do have to a bit more careful. The bits that represent inc are incremented, whilst a value based on that number and the argument goes into the return value. Again, we can in principle specify it by brute force, by enumerating every possible state of the bit store on code entry and code exit. Which tells us that it is a "function", or if you want to be pedantic about it, "code which calculates a function". |
Frederick Virchanza Gotham <cauldwell.thomas@gmail.com>: Mar 05 09:59AM -0800 Let's say I have one program and one shared library on a *nix computer. I build my program to link dynamically with the library as follows: g++ -o prog prog.cpp -l:libmonkey.so So let's say that this produces an executable file that works fine. Next I change the build command to the following: g++ -o prog prog.cpp And so now of course I get a linker error because of unresolved symbols (I'm missing the functions implemented in the library). To overcome this linker error, I change the build command again: g++ -o prog prog.cpp -Wl,--unresolved-symbols=ignore-in-object-files So now we get a viable executable file, but when we run it, it segfaults. It segfaults when it tries to access something from the shared library. So next I make a one-line change at the beginning of 'main': int main(void) { dlopen("libmonkey.so", RTLD_NOW|RTLD_GLOBAL); // The rest of main goes here } So now the program works fine. I think however, that this strategy only works when the program doesn't use global variables which are exported from the library. That is to say, it works fine for exported functions but not for exported global variables. Am I right here? I have more testing to do on this, but I need to get this working. I need to remove the library from the 'NEEDED' section in the program's ELF file, and instead I have to use 'dlopen' at runtime to load it in. How can I get this to work with the global variables also? I've tried declaring the global variable as a weak symbol in the program, and that seems to work, but I don't want to have to go looking for a list of all the global objects exported from the shared library. Also I realise that things get complicated if there's a global object in the program whose constructor accesses the shared library (in which case I need to make use of __attribute__((constructor)). But I'll deal with thay conundrum later. |
Christian Gollwitzer <auriocus@gmx.de>: Mar 05 07:12PM +0100 Am 05.03.23 um 18:59 schrieb Frederick Virchanza Gotham: > So now the program works fine. > I think however, that this strategy only works when the program doesn't use global variables which are exported from the library. That is to say, it works fine for exported functions but not for exported global variables. Am I right here? > I have more testing to do on this, but I need to get this working. I need to remove the library from the 'NEEDED' section in the program's ELF file, and instead I have to use 'dlopen' at runtime to load it in. As always, I'm questioning this NEED. Why do you want to load the required library at runtime? Do you want to adjust the path at initialization? If it is only about packaging the library with the application, you could use the run-path when linking; e.g. say your library is distributed in a lib folder alongside your executable, then -Wl,-rpath,'$ORIGIN'/lib in the linker line would do that. Another alternative is to write a small shell script which adjusts LD_LIBRARY_PATH before invoking the binary. I can see the need for dlopen() only in case where the functionality is somewhat optional, like in a plugin system. Christian |
Frederick Virchanza Gotham <cauldwell.thomas@gmail.com>: Mar 05 11:11AM -0800 > As always, I'm questioning this NEED. I'm combining a console program and a GUI program into one program (i.e. one executable). Depending upon the command-line arguments to the program, it might enter into GUI mode, and if it does, it needs to load the GUI libraries. But if it runs in console mode, I don't want the system to need to have the Gui libraries installed. |
Christian Gollwitzer <auriocus@gmx.de>: Mar 05 10:45PM +0100 Am 05.03.23 um 20:11 schrieb Frederick Virchanza Gotham: > I'm combining a console program and a GUI program into one program (i.e. one executable). > Depending upon the command-line arguments to the program, it might enter into GUI mode, and if it does, it needs to load the GUI libraries. > But if it runs in console mode, I don't want the system to need to have the Gui libraries installed. This usually works by exporting a known entry function from the library, load the library by dlopen() and find the function using dlsym(). Put all the functionality into the library, so that you can invoke the GUI stuff with a simple call. It doesn't make sense to have global variables in the main program have influenced by loadable library. If you need a lot of the functionality of the main program in the library, then instead put this functionality in a library if its own (say, libengine.so). Then the main program reduces to if (std::string(argv[1] == "-gui") { dlopen(); run_gui = dlsym("..."); run_gui(); } else { run_cmdline(); } Link both this main and the GUI library with libengine.so. Christian |
"Chris M. Thomasson" <chris.m.thomasson.1@gmail.com>: Mar 04 03:25PM -0800 On 3/3/2023 8:38 PM, Bonita Montero wrote: >> Not until you model it in something like Relacy. >> No time right now to read all of your code and verify it. > Sorry, the code is trivial from the MT-perspective. I have seen too many bugs in code that others have labeled trivial before... Btw, I am busy on another project. :^) |
"Chris M. Thomasson" <chris.m.thomasson.1@gmail.com>: Mar 04 03:26PM -0800 On 3/4/2023 11:07 AM, Bonita Montero wrote: > ... > string dequeued( stringQueue.dequeue() ); > That's all. Take the time to model it in a race detector. |
Bonita Montero <Bonita.Montero@gmail.com>: Mar 05 05:18AM +0100 Am 05.03.2023 um 00:26 schrieb Chris M. Thomasson: > Take the time to model it in a race detector. You are an idiot; no one needs a race-detector for such simple code. |
Bonita Montero <Bonita.Montero@gmail.com>: Mar 05 05:19AM +0100 Am 05.03.2023 um 00:25 schrieb Chris M. Thomasson: > I have seen too many bugs in code that others have labeled > trivial before... Btw, I am busy on another project. :^) Idiot. You didn't have a look at my code. |
Tim Rentsch <tr.17687@z991.linuxsc.com>: Mar 05 08:38AM -0800 >> Even better, that you updated to more modern software. :-o > I believe the first time that I've taken issue with Tim Rentsch, but, > yes :-) Note that my comment is not about tools but about matters of visual presentation. The tools I use have no problem dealing with long lines but what tools do is not the high order bit here. There are good human factors reasons to limit line length to somewhere close to 80 characters, and that point is what I am hoping to convey. Note also that I am not the only newsgroup member, nor even the first, to complain about Alf's idiosyncratic style choices. |
Tim Rentsch <tr.17687@z991.linuxsc.com>: Mar 05 08:43AM -0800 > On 2023-02-24 4:51 PM, Tim Rentsch wrote: [...] >> to 80 characters, as many coding standards and style guidelines >> recommend. > Even better, that you updated to more modern software. :-o I'm sad to say that, coming from you, this statement doesn't surprise me. AFAIAA more people complain about problems your tools cause than there are for the tools used in my postings. |
"Chris M. Thomasson" <chris.m.thomasson.1@gmail.com>: Mar 05 01:37PM -0800 On 3/4/2023 8:18 PM, Bonita Montero wrote: > Am 05.03.2023 um 00:26 schrieb Chris M. Thomasson: >> Take the time to model it in a race detector. > You are an idiot; no one needs a race-detector for such simple code. There is nothing wrong with using a race-detector. Model the simple code in the detector, then move it into your C++ code. There is nothing wrong with modeling a lock-based and/or lock-free, wait-free synchronization scheme in a race detector, before, you flesh it out in real code. |
"Chris M. Thomasson" <chris.m.thomasson.1@gmail.com>: Mar 05 01:41PM -0800 On 3/4/2023 8:19 PM, Bonita Montero wrote: >> I have seen too many bugs in code that others have labeled >> trivial before... Btw, I am busy on another project. :^) > Idiot. You didn't have a look at my code. I did, but not long enough to verify it as 100% kosher. |
Pawel Por <porparek@gmail.com>: Mar 05 03:34AM -0800 > What behavior made you to draw that conclusion ? I cannot see any Dog's constructor or operator to be called while calling MyList::push_front(). No __PRETTY_FUNCTION__ output (refer to the code below). > What are we expected to see in this output ? I expect the Dog::operator=(Dog&&) to be called I'm aware that __PRETTY_FUNCTION__ shows the following but why the Dog::operator=(Dog&&) isn't called ? void MyList<T>::push_front(T&&) [with T = Dog] The updated code is as follows (I'm using g++ 9.4.0 Ubuntu 20.04) #include <iostream> #include <forward_list> #include <utility> template <typename T> void p(const T &v) { std::cout << v << std::endl; } struct Dog { Dog() { p(__PRETTY_FUNCTION__); } Dog(const Dog&) { p(__PRETTY_FUNCTION__); } Dog(Dog&&) { p(__PRETTY_FUNCTION__); } Dog& operator=(const Dog&) { p(__PRETTY_FUNCTION__); return *this; } Dog& operator=(Dog &&) { p(__PRETTY_FUNCTION__); return *this; } }; template<typename T> struct MyList { void push_front(T &&v) { p(__PRETTY_FUNCTION__); T x = std::move( v ); (void) x; } }; int main() { MyList<Dog> ml; std::forward_list<Dog> fl; Dog dog; p("ml.push_front"); ml.push_front(std::move(dog)); p("fl.push_front"); fl.push_front(std::move(dog)); } |
Pawel Por <porparek@gmail.com>: Mar 05 10:20AM -0800 > > What are we expected to see in this output ? > I expect the Dog::operator=(Dog&&) to be called I expect the Dog::Dog(Dog&&) to be called (sorry for confusion) |
Andrey Tarasevich <andreytarasevich@hotmail.com>: Mar 05 10:27AM -0800 On 03/05/23 3:34 AM, Pawel Por wrote: >> What behavior made you to draw that conclusion ? > I cannot see any Dog's constructor or operator to be called while calling MyList::push_front(). No __PRETTY_FUNCTION__ output (refer to the code below). Um... What? But your code outputs Dog::Dog(Dog&&) from inside 'MyList::push_front()'. This is clearly a call to Dog's constructor. Why do you say that you "cannot see any Dog's constructor [...] to be called"? And that still does not allow you to differentiate between lvalue reference and rvalue reference. So, my question still stands. >> What are we expected to see in this output ? > I expect the Dog::operator=(Dog&&) to be called Why? The code you provided does not use assignment operator at all. Why would you expect assignment operator to be called? > I'm aware that __PRETTY_FUNCTION__ shows the following but why the Dog::operator=(Dog&&) isn't called ? Again, show me the exact location where you expect the assignment operator to be called. -- Best regards, Andrey |
Andrey Tarasevich <andreytarasevich@hotmail.com>: Mar 05 10:30AM -0800 On 03/05/23 10:20 AM, Pawel Por wrote: >>> What are we expected to see in this output ? >> I expect the Dog::operator=(Dog&&) to be called > I expect the Dog::Dog(Dog&&) to be called (sorry for confusion) But it _is_ called. Here's the output I get from your code Dog::Dog() ml.push_front void MyList<T>::push_front(T&&) [with T = Dog] Dog::Dog(Dog&&) fl.push_front Dog::Dog(Dog&&) -- Best regards, Andrey |
Tim Rentsch <tr.17687@z991.linuxsc.com>: Mar 05 08:20AM -0800 > The problem isn't about alignment, but that the code uses a pointer to > signed char. The standard allows inspecting bytes as unsigned char, > but has no special allowance for signed char. This comment is at best misleading. A static_cast to (unsigned char *) isn't allowed any more than a static_cast to (int8_t *) is. |
MarioCPPP <NoliMihiFrangereMentulam@libero.it>: Mar 05 05:14PM +0100 Could sb explain me what is the semantic meaning of that syntax and what possible use-cases does a Type && have ? A reference is an "hidden" immutable pointer to an object (with some syntactic sugar to access members by DOT and not by ->), which should also a be warranty to point to a valid object (no nullptr). But a Type && seems to be also able to point to ... to what ? What is for ? -- 1) Resistere, resistere, resistere. 2) Se tutti pagano le tasse, le tasse le pagano tutti MarioCPPP |
You received this digest because you're subscribed to updates for this group. You can change your settings on the group membership page. To unsubscribe from this group and stop receiving emails from it send an email to comp.lang.c+++unsubscribe@googlegroups.com. |
No comments:
Post a Comment