Hi,
My platform has 32 bit words, and an `unsigned int' corresponds to 32
bits. Also an `unsigned long long' corresponds to 64 bits.
If I declare a type of `unsigned long long', can I assume that my
compiler would correctly interpret any operation I do on this type if I
visualise it as if it's the native word size? I guess that's the
transparency the compiler ought to provide, right?
For example the atomicity of operations would differ, but that's
perhaps not defined in C. Is there anything else that would work
differently that's defined in C?
The question's a little unclear to me; I'm not entirely
sure what's worrying you. At the risk of missing your point:
First, the "nativeness" of a data type isn't really a
concern of C. All you know -- and usually, all you need --
is that the type behaves properly when you use it in a C
program. The machinations that C goes through to get this
to happen are mostly invisible and mostly irrelevant: it
doesn't matter whether the platform performs floating-point
division with an instruction or with a subroutine.
The "nativeness" can obtrude when you start relying on
a type to have characteristics beyond those guaranteed by C.
Atomicity is one such: C's formal model of execution is almost
purely single-threaded and synchronous, so there's no other
"activity" that could observe whether an action is atomic or
not. (I said "almost" because there's one small exception:
signals can occur asynchronously, and there's a sig_atomic_t
type that has a few atomicity guarantees.) Similarly, C says
nothing about the speed of operations on different types; adding
a pair of unsigned long longs might take about the same amount
of time as adding a pair of ints, or might take four times as
long, or forty times as long.
Getting back to your example of unsigned long long: C
promises that it's an integer type, that all its values are
non-negative, that they range from 0 through ULLONG_MAX, that
ULLONG_MAX is one less than a power of two, and that the power
in question is 64 or greater. C further defines how the various
operators work on the available values, what the results the
operators yield, and under what circumstances the operators
are not guaranteed to work (e.g., ULLONG_MAX % 0UL). Finally,
C defines how unsigned long long values are used or produced by
various library functions: printf, strtoull, and so on. As long
as you stick to the defined operations (and provided that there
aren't bugs in the C implementation), you'll get the results
the Standard promises. When you start relying on things like
timing or atomicity, you need to consider the characteristics
of a particular implementation of C, not those of C itself.