Wednesday, November 20, 2019

Digest for comp.lang.c++@googlegroups.com - 18 updates in 4 topics

Soviet_Mario <SovietMario@CCCP.MIR>: Nov 20 07:55PM +0100

I am trying to create a statically linked library in the
said IDE.
I would not want to include many QT features for now
so, what is the STANDARD C++ way to get
unsigned 8 bits integer type ?
 
I fear that unsigned char is system dependent (and even if
there are "wider" explicitely supported types, no plain char
type seems to warranty to be 8 bits wide).
 
The solution of creating an unnamed structure with a "bit
field like
struct {unsigned Pixel : 8} Mask;
gives me a warning like : 3 byte PADDING used to align the
struct Mask.
 
Now I don't know whether this padding would exist also in
ARRAY dynamic allocation (I'm not speaking for just the
first address of the array, but for EVERY SINGLE ITEM in it,
wasting as much as 3 times the space required !)
 
How to get rid of such alignment feature ?
 
in Visual Studio there were align / pad directives, but here
on QT I dunno anything.
 
I don't care a lot about fastness of access, but need a true
compact byte array (QT has its own, but I will need to
communicate with a Gambas program using the static library,
so I'd be not happy to interface QT internals with Gambas,
I'd prefer a standard C++ types-based solution).
 
long ago CHAR was 8 bit wide, but now it seems to be
platform dependent, and more often "a word" wide.
 
QT has its explicitely sized integers (even if no 8-bit sized)
 
TY
 
 
--
1) Resistere, resistere, resistere.
2) Se tutti pagano le tasse, le tasse le pagano tutti
Soviet_Mario - (aka Gatto_Vizzato)
Soviet_Mario <SovietMario@CCCP.MIR>: Nov 20 08:12PM +0100

Il 20/11/19 19:55, Soviet_Mario ha scritto:
 
Uhm, from some search, it seems that a "pragma pack" exist.
I still have to read it, though
 
 
 
--
1) Resistere, resistere, resistere.
2) Se tutti pagano le tasse, le tasse le pagano tutti
Soviet_Mario - (aka Gatto_Vizzato)
Soviet_Mario <SovietMario@CCCP.MIR>: Nov 20 08:22PM +0100

Il 20/11/19 19:55, Soviet_Mario ha scritto:
 
 
 
this
 
#pragma pack(push,1) // pushes the current alignment setting
on an internal stack and then optionally sets the new alignment.
typedef struct clsByte
{
union
{
unsigned PixelMask : 8;
};
} clsByte;
#pragma pack(pop) // restores former default value
 
seems to have suppressed the warning
 
A further question (general)
 
as I am accessing BYTES (not multibyte object), apart from
performance issues, do you think there could be a
portability issue ?
I am thinking that addressing strict bytes should require
accessing EVERY non aligned address in general (string
operations on ascii chars and odd length would be impossible
otherwise).
 
Is it correct ?
 
--
1) Resistere, resistere, resistere.
2) Se tutti pagano le tasse, le tasse le pagano tutti
Soviet_Mario - (aka Gatto_Vizzato)
Jorgen Grahn <grahn+nntp@snipabacken.se>: Nov 20 07:34PM

On Wed, 2019-11-20, Soviet_Mario wrote:
 
> I am trying to create a statically linked library in the
> said IDE.
 
The IDE doesn't matter; the Qt libraries do matter.
 
> I would not want to include many QT features for now
> so, what is the STANDARD C++ way to get
> unsigned 8 bits integer type ?
 
uint8_t, just like in C. Or, I guess it's really std::uint8_t.
 
> I fear that unsigned char is system dependent (and even if
> there are "wider" explicitely supported types, no plain char
> type seems to warranty to be 8 bits wide).
...
> long ago CHAR was 8 bit wide, but now it seems to be
> platform dependent, and more often "a word" wide.
 
No; a char is rarely more than 8 bits nowadays. You may be thinking
of wchar_t, but that's something different.
 
> QT has its explicitely sized integers (even if no 8-bit sized)
 
Qt has its own versions of most things ... are you sure you need it?
 
/Jorgen
 
--
// Jorgen Grahn <grahn@ Oo o. . .
\X/ snipabacken.se> O o .
David Brown <david.brown@hesbynett.no>: Nov 20 10:03PM +0100

On 20/11/2019 19:55, Soviet_Mario wrote:
> I would not want to include many QT features for now
> so, what is the STANDARD C++ way to get
> unsigned 8 bits integer type ?
 
uint8_t from <stdint.h>, or std::uint8_t from <cstdint>.
 
> "wider" explicitely supported types, no plain char type seems to
> warranty to be 8 bits wide).
> -based solution).
 
<snip>
 
> long ago CHAR was 8 bit wide, but now it seems to be platform dependent,
> and more often "a word" wide.
 
The size of "char" has always been platform dependent. Whether plain
"char" is signed or unsigned has also always been platform dependent.
 
On most systems, "char" is 8-bit, but the signedness varies - always
specify it explicitly ("signed char" or "unsigned char") when it is
relevant. Typically you only find char bigger than 8-bit on DSP's or
other specialist processors.
 
But if you stick to the standard type "uint8_t", you get exactly what
you ask for. (If the platform doesn't support 8-bit char, the type
won't exist and the code won't compile. But very little code needs to
be /that/ portable.)
Paavo Helde <myfirstname@osa.pri.ee>: Nov 20 11:28PM +0200

On 20.11.2019 20:55, Soviet_Mario wrote:
> I would not want to include many QT features for now
> so, what is the STANDARD C++ way to get
> unsigned 8 bits integer type ?
 
Why do you need an exactly 8-bit type? And how this is related to QT or
static linking, or to an IDE?
 
In general, if you need an unsigned 8-bit type, use std::uint8_t.
Frederick Gotham <cauldwell.thomas@gmail.com>: Nov 20 01:19AM -0800

Typically, when a cross-compiler is installed properly on a computer, do you need to explicitly invoke it with "--sysroot=/opt/targetfs", or is this parameter already implied if the cross-compiler is properly installed?
 
Right now I'm working on an embedded Linux project, and I'm using Buildroot to produce a minimalistic Linux installation with only the programs and libraries I need.
 
I see that some 3rd party packages, (i.e. NOT the one's built into Buildroot), invoke the correct cross-compiler but they don't give the "--sysroot" parameter.
 
For example, a normal native compilation would be:
 
g++ main.cpp -o prog
 
And a correct cross-compilation would be:
 
CXX = /opt/src/build/output/host/bin/x86_64-buildroot-linux-gnu-g++
SYSROOT = /opt/src/build/output/host/x86_64-buildroot-linux-gnu/sysroot
 
$(CXX) --sysroot=$(SYSROOT) main.cpp -o prog
 
I see however that some packages are leaving out the sysroot parameter, and so they're just doing:
 
$(CXX) main.cpp -o prog
 
This predictably fails if the host and the target have different CPU's, for example if my office PC is x86_64 and my target is embedded Linux ARM aarch64.
 
On my current project though, the host and the target have the same CPU, and so if you leave out the "--sysroot" parameter then the program ends up linking with shared libraries installed on the host. Sometimes this happens without any compiler warning or error!
 
So how are cross-compilers supposed to work? If they are installed properly, do you need to give them the "--sysroot" parameter?
red floyd <dont.bother@its.invalid>: Nov 20 11:20AM -0800

On 11/20/2019 1:19 AM, Frederick Gotham wrote:
 
> This predictably fails if the host and the target have different CPU's, for example if my office PC is x86_64 and my target is embedded Linux ARM aarch64.
 
> On my current project though, the host and the target have the same CPU, and so if you leave out the "--sysroot" parameter then the program ends up linking with shared libraries installed on the host. Sometimes this happens without any compiler warning or error!
 
> So how are cross-compilers supposed to work? If they are installed properly, do you need to give them the "--sysroot" parameter?
 
This question more properly belongs on a Linux or GNU forum.
David Brown <david.brown@hesbynett.no>: Nov 20 09:19AM +0100

On 19/11/2019 22:20, Melzzzzz wrote:
> function syntax, this one has sence only on unspecified return type,
> for what auto keyword is handy. I will never use it in my code as it can
> serve just to bring confusion...
 
I expect that most people will continue to use the normal C++ function
syntax for the majority of their code. "auto" functions certainly have
their use cases, and where it is useful, it is very useful:
 
template <class A, class B>
auto sum(A a, B b) -> decltype(a + b)
{
return a + b;
}
 
You can't do write that as neatly or as well without "auto". This is
why the trailing return type syntax was invented.
 
It can also be convenient for simple, local functions using return type
deduction:
 
auto foo(int a)
{
return a * 1.2345;
}
 
This is especially true for returning more complicated types (iterators,
lambdas, etc.) - just like the use of "auto" for variables.
 
But I really do not see any benefit of writing:
 
auto foo(int a) -> double
{
return a * 1.2345;
}
 
It adds nothing to the language or the code. (Clearly the language had
to allow it, in order to allow useful cases, but that does not mean you
have to /use/ it.) The only argument I have heard in its favour is
"consistency" - but it is a foolish consistency, IMHO, and inconsistent
with all the rest of C++ code.
 
Time will tell - it is the only way to find out if this syntax becomes
the fashion or not.
 
(It would be a little different if a new function-specific keyword had
been added, like "def" or "func". Then there would be an advantage in
having it, making the function definition stand out more - I know that
is something that some people would prefer. But it would have to be a
unique keyword - another overload of "auto" does not help here.)
Christian Gollwitzer <auriocus@gmx.de>: Nov 20 11:12AM +0100

Am 19.11.19 um 21:31 schrieb Alf P. Steinbach:
 
> But the committee could have chosen to use operator notation, like the
> lambda notation:
 
>    [] foo() -> int
 
Actually, they could have chosen to omit the type means "auto". In old
C, omitting the type meant "int", which is obviously not useful any
longer. Making "no type" into "auto" could make C++ closer to other
modern languages. I.e.
 
f(x, y) { return x+y; }
 
could become
 
auto f(auto x, auto y) { return x+y; }
 
which is
 
template <typename Tx, Ty>
auto f(Tx, x, Ty y) { return x+y; }
 
 
without all the cruft that the compiler can figure out by itself.
 
Christian
"Öö Tiib" <ootiib@hot.ee>: Nov 20 02:16AM -0800

On Wednesday, 20 November 2019 10:19:56 UTC+2, David Brown wrote:
> {
> return a * 1.2345;
> }
 
No way out of it. It is in language so we all must be capable
to read it (even if we dislike it and refuse to write it).
 
What I think is that it is half-solution of moving C++ from type
being smeared around name towards type last. Lot of other
languages, (including number of C-like languages) have
type last:
 
function foo(a: integer): double;
 
Designers of those languages considered it more clear
and readable.
 
Other example from C++: Many consider using "using" instead of
"typedef" more readable for declaring type aliases.
Typedef:
 
typedef double(*Portal)[4];
typedef std::string Contact;
typedef std::vector<Portal> Portals;
typedef std::map<Contact, Portals> PortalsOfContact;
 
Using:
 
using Portal = double(*)[4];
using Contact = std::string;
using Portals = std::vector<Portal>;
using PortalsOfContact = std::map<Contact, Portals>;
 
Nah ... matter of taste? However the result that we have both in
language is kind of anarchistic, since all users of it must be
capable to understand both when reading and when writing
have to pick (or to ask what to pick or to argue it clear what
we pick).
 
Also it is only half-solution since when declaring variables,
parameters or members we have type that is smeared around
name anyway and there are no alternatives to have it last.
 
> Time will tell - it is the only way to find out if this syntax becomes
> the fashion or not.
 
My glass ball says that like it is it will just troll up discussions of
readability (instead of discussions of actual technical problems)
forever. Perhaps it is sort of cheap publicity stunt:
fashion controversy -> novice questions -> heated discussions
-> more hits -> more popularity. From engineering perspective
that all is utterly worthless.
 
However if a way to have "type last" for parameters, members
and variables will also be added by some C++2013 or C++2016
then I will switch over into proponent of that style too. ;-)
"Öö Tiib" <ootiib@hot.ee>: Nov 20 04:25AM -0800

On Wednesday, 20 November 2019 12:12:20 UTC+2, Christian Gollwitzer wrote:
 
> template <typename Tx, Ty>
> auto f(Tx, x, Ty y) { return x+y; }
 
> without all the cruft that the compiler can figure out by itself.
 
Oh so easy is to write wrappers around operator+.
But what is the point of it? There must be something more complicated
than operator+.
 
So lets say that we have f that is result of something more complicated.
What about callers of f? Lets say its caller gets several values
also from similar functions/members that return who knows what
and has to return a mapping from all v-s to what f returns there.
Something like:
 
auto makeMapping(int i)
{
using PromoterHapperFOfVacuole = ???; // what it is?

PromoterHapperFOfVacuole ret;
 
for (auto v = getFirstVacuole(i); v.isUseful(); v = v.getNext()) {
// here we use your f
ret[v] = f(producePromoter(v.vaginulate(),hatchHapper(p.glaze(), v.jabbered()));
}
return ret;
}
 
What *is* the type of mapping? From where to take
that unavoidable "cruft" here? Reverse engineer
somehow from those getFirstVacuole etc? How?
Also sorry for using more meaningful function names than f.
"Öö Tiib" <ootiib@hot.ee>: Nov 20 06:05AM -0800

On Wednesday, 20 November 2019 14:26:11 UTC+2, Öö Tiib wrote:
 
> for (auto v = getFirstVacuole(i); v.isUseful(); v = v.getNext()) {
> // here we use your f
> ret[v] = f(producePromoter(v.vaginulate(),hatchHapper(p.glaze(), v.jabbered()));
 
Sorry did not try it ... I meant something like:
 
auto p = producePromoter(v.vaginulate(), i);
ret[v] = f(p, hatchHapper(p.glaze(), v.jabbered()));
 
scott@slp53.sl.home (Scott Lurndal): Nov 20 02:13PM


> function foo(a: integer): double;
 
>Designers of those languages considered it more clear
>and readable.
 
Did they? Or were they simply following some earlier example?
 
For example, ALGOL 68:
proc abs max = ([,]real a, ref real y, ref int i, k)real:
 
 
ALGOL 60 was more like KNR C:
 
procedure Absmax(a) Size:(n, m) Result:(y) Subscripts:(i, k);
value n, m; array a; integer n, m, i, k; real y;
"Öö Tiib" <ootiib@hot.ee>: Nov 20 08:34AM -0800

On Wednesday, 20 November 2019 16:14:02 UTC+2, Scott Lurndal wrote:
 
> >Designers of those languages considered it more clear
> >and readable.
 
> Did they? Or were they simply following some earlier example?
 
Certainly there were plenty of examples of every kind.
 
I meant designers of newer C-like languages Go, Rust and
Swift.
 
They switched to type being last in declarations while
all previous attempts of "better" C, (C++, Objective-C,
Java, D and C#) had type first or around name like in C?
 
 
> ALGOL 60 was more like KNR C:
 
> procedure Absmax(a) Size:(n, m) Result:(y) Subscripts:(i, k);
> value n, m; array a; integer n, m, i, k; real y;
 
Sure there have been also plenty of mixed and inconsistent
examples.
Manfred <noname@add.invalid>: Nov 20 06:46PM +0100

On 11/18/2019 6:49 PM, Alf P. Steinbach wrote:
> types, but I don't feel that this can be the best solution.
 
> Like, it feels like a kludge, somewhat dirty.
 
> - Alf
 
I'll steer away from the discussion about trailing return type (which
has been discussed ad nauseam)
 
Substitution failure in this case happens for instantiation of a class
member (m), after specialization of the template S.
So it looks like the error occurs too late to be eliminated by SFINAE.
 
I didn't check the standard, but Bjarne's book on SFINAE says that the
compiler eliminates a candidate if the associated substitution would
lead to a "template specialization that would be nonsensical" - now,
define "nonsensical".
He says: "A template specialization is considered nonsensical if it
would lead to a type error." And further on that only declarations are
considered, neither function definitions nor definitions of class
members are considered.
 
So, slippery, but we can say that SFINAE is not a fully baked tool for
template selection. He himself suggests enable_if as a more specific
tool for the task.
I would say that even if enable_if looks dirty, this is because of its
syntactic ugliness, and it is probably the right choice.
Soviet_Mario <SovietMario@CCCP.MIR>: Nov 20 12:40AM +0100

Il 19/11/19 20:49, Soviet_Mario ha scritto:
 
> I'm confused about the pointer "nullity" management.
 
> Long ago casting a 0 had been enough :\
 
tnx to you all for advices.
I'll avoid the extra unessential cast (I hadn't thought of
trying to remove it)
 
--
1) Resistere, resistere, resistere.
2) Se tutti pagano le tasse, le tasse le pagano tutti
Soviet_Mario - (aka Gatto_Vizzato)
scott@slp53.sl.home (Scott Lurndal): Nov 20 02:15PM


>now, WHAT exactly is the nullptr ? Is it really different
>from ZERO (all-zeroes-bit pattern of the word size) ?
 
A NULL pointer need not have the value zero; I recall an
architecture where NULL pointers were indicated by the
sentinal value EEEEEE (yes, 6 4-bit digits).
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: