 |
Typecast ('(type)') |
The typecast operator forces an expression to behave as an object of a given type. It uses the
following syntax:
(type) expr
The expression expr will be interpreted as having type type. It may
be any simple type (modified or unmodified), enumeration,
structure, union, user
defined type created using typedef, void type, or
an anonymous type (see asterisk for more information about anonymous
types). Here is an example list of valid typecast operators:
(int)
(unsigned long int)
(signed)
(enum foo)
(struct foo)
(mytype) assuming that 'mytype' is defined with 'typedef'
(void)
(char *)
(void *)
(struct foo *)
(void (*)(int))
(int (*[])(char*))
Typecast operator is very powerful in C, and may be used for conversion nearly everything
to anything. For example, it is legal to convert an integer value to a pointer, so you
can perform direct access to the memory (don't do this if you don't know exactly what are you
doing). For example, '(char*)19456'
converts integer 19456 to a char pointer, which
may be dereferenced further using the dereference operator. So,
* (char*)19456 = 255;
stores 255 in the memory at the absolute address 19456 (this is the first byte of the LCD memory
on TI-89 and TI-92+). The more drastic example is
((void(*)())10000)();
which calls the subroutine located at absolute address 10000 (first, the typecast operator
'(void(*)())'
converts 10000 to the pointer to the function, then the
parentheses operator '()'
is used to call the function).
Note that nearly the whole TIGCC library, when used in "nostub" mode,
is implemented using the typecast operator which converts TIOS jump table entries to pointers
to functions. For example, ClrScr is defined as
'(*(void(**)(void))(*(long*)0xC8+0x678))'
, which is nothing other than a complex
typecast. So, when you do
ClrScr ();
in your program, the preprocessor replaces it with
(*(void(**)(void))(*(long*)0xC8+0x678))();
However, typecast operator cannot be used to convert a scalar type to a
structure or union (and vice versa), or to convert one non-scalar type into an incompatible
non-scalar type. That's why casting to structures and unions are rarely valid.
Casting to a void means that you want to discard the result of the expression.
Casting to or from a floating point type are internally executed using the
flt and trunc functions. See the description of
these functions for more info.
Note: GNU C extends the usage of typecast operator to allow making
cast constructors, which are probably the most powerful
GNU C extensions. It also allows much more flexibility in
casting to an union types.