the real difference is in decl0 where we can use external_sym
just fine also for function definitions, we don't have to use
external_global_sym. Setting VT_EXTERN in external_sym isn't
necessary either (the type will have it set if necessary).
The rest is tidying: removing unused arguments and moving
some code around.
we can register a top-level exception filter which does
nothing else than call into _XcptFilter (provided by
the default C runtime environment) and signal handlers
for the few POSIX signals that Windows can handle start
working (that includes e.g. SEGV).
anonymous struct members were somewhat broken as the testcase
demonstrates. The reason is the jumping through hoops to fiddle
with the offsets I once introduced to avoid having to track
a cumulative offset. That's now not necessary anymore and actively
harmful, doing the obvious thing is now better.
see testcase, when the inner array dimension of multi-dimensional
VLAs isn't given TCC was generating invalid vstack accesses.
Those are actually invalid, so just diagnose them.
this test is run only on i386 so its failing went unnoticed for
a while, since 1fd3709379. IS_ASM_SYMs should not be tested
for conflicting types, the C typing overrides.
_Noreturn, just like __attribute__((noreturn)), is ignored.
I also added stdnoreturn.h, in all its glorious uselessness.
_Alignas only works for integer expressions right now. In order
to comply, we need:
- _Alignas(type) -> _Alignas(_Alignof(type)).
- stdalign.h as soon as it is done.
Note: DR 444 is supported; it works on struct members.
Signed-off-by: Devin Hussey <husseydevin@gmail.com>
see testcases. A local 'extern int i' declaration needs to
refer to the global declaration, not to a local one it might
be shadowing. Doesn't seem to happen in the wild very often as
this was broken forever.
in presence of invalid source code we can't rely on the
next token to determine if we have or haven't already parsed
an initializer element, we really have to track it in some separate
state; it's a flag, so merge it with the other two we have (size_only
and first). Also add some syntax checks for situations which
formerly lead to vstack leaks, see the added testcases.
Also added a test yielding a failure with the previous definition,
i.e. when using: (va_end(ap));
The test also checks potentially incorrect va_start() definition.
sometimes abstract decls in parameter lists left the returned name
uninitialized potentially leading to segfaults, like in
int f(int ()) {
return 0;
}
Deal with this.
like on 'enum myenum { L = -1 } L;'. It's a bit tedious as
there are two paths (for global vs local symbols), and because
the scope and enum_val share same storage.
the ABIs (and other compilers) extend sub-int return values in the
caller. TCC extends them in the callee. For compatibility with
those other compilers we have extend them in the caller as well.
That introduces a useless double extension in pure TCC-compiled code,
but fixing that generally requires that the code generator of TCC would
understand sub-int types. For the time being bite the bullet.
encode most things in Syms, do only as much work as necessary
(e.g. pending cleanups), don't track scopes in a large
structure (instead encode the scopes with cleanups directly
in the cleanups tree). Removes ca. 120 lines of code.
old implementation use only a global static array for storing
ScopeTracker which have the advantage to be fast, but you can't
use cleanup in a function that have move than SCOPE_TCK_STORE_SIZE
scopes.
I don't want to use only dynarray_* as it would slow down tcc for
every functions, so I keep both stores.
The major difficulty was to handle cleanup when a goto happen
to do so, I've had a "ScopeTracker" struct.
I can't use local_scope because that would not work with code like below
as local_scope would be at the same level:
{
char * __attribute__ ((cleanup(clean_function))) str = "hej";
goto next;
}
{
next:
}
read() is allowed to short-read, and return less bytes then requested.
The caller must restart read() when this happens (and they want more
bytes).
This patch is still buggy, because errors are not always checked.
Still, less buggy than before.
symbols are local when defined and referred to from the executable.
Also, we need to relocate the .got section when this is a static link
(our static linking effectively generates code as if this were a dynamic
link with PLT and GOT, and then emulates the runtime loader).
Support multiple __label__ declarations at the beginning of a block
as long as they're contiguous.
gcc and clang accept:
{ __label__ a,b; __label__ c; /*...*/ }
.
Tcc would fail it. This patch makes it accept it.
The patch:
- if (tok == TOK_LABEL) {
+ while (tok == TOK_LABEL) {