memcmp does 8-byte reads if length > 8, which might cross a page-boundary and
crash. Not strictly a memcmp bug, since manpage doesn't say that memcmp must stop at
first difference. Linux doesn't crash because it only does 4/8-byte reads on 4/8-byte aligned
addresses, hence it can never cross a page boundary.
Fix this by making sure that what we request from memcmp is entirely readable.
You can now build with both the internal (patched) LLVM 2.7,
or an external LLVM 2.8rc.
To build with external do this:
./configure --enable-llvm --with-system-llvm=/path/to/llvm-config
This will link against the external LLVM's .a files (they are PIC), so
LLVM will stay only a build time dependency.
* llvm2.8:
Regenerate configure and Makefile.
LLVM 2.8 changed llvm.mem{cpy,move,set}.* to take 5 arguments.
LLVM 2.8 API update.
Don't cast the iterator directly.
Use CallSite instead of CI->getOperand.
Support building with external LLVM 2.8.
Conflicts:
libclamav/c++/Makefile.in
libclamav/c++/bytecode2llvm.cpp
libclamav/c++/configure
Use AutoUpgrade to upgrade these calls.
Intrinsic::getDeclaration can't be used because in 2.7 it needs 1 type,
in 2.8 it needs 2/3, and there is no function to query how many it needs.
off_t is 64-bit, size_t is still 32-bit and that causes unexpected integer
promotion here:
map_off = map->len - 2048
First the unsigned subtraction is performed, and then the unsigned (!) value
is sign-extended to 64-bit. Hence a negative value becomes positive, which is
wrong.
Avoid quadratic load times: run module passes at the end, and run
rtcheck inserter at the end also.
Also optimize away some simple situations that the compiler couldn't,
like result of __is_bigendian() which is a constant at load time (but not at
compile time).
If we would have run LLVM's -O1 optimizers these would have been
optimized already, but we don't do that for 2 reasons:
- optimizations may introduce new bugs
- may take a bit longer time
Just run some simple transforms, and some custom optimizations for the bigendian
case.
GCC (4.4 at least) requires and creates functions with 16-byte stack alignment
on 32-bit Linux too.
If they happen to use SSE instructions they will crash if incoming stack
alignment is not 16-byte.
LLVM claims that 4-byte stack alignment is the standard, and it only aligns to
4-byte, hence the crash. Apparently older versions of GCC/glibc would crash
if it set alignment to 16-byte.
But since the oldest GCC we support is 4.1.2, and disable LLVM on anything older
just set stack alignment to 16-byte for all functions. LLVM will realign stack
as needed. To be safe turn this on only on Linux.
This should really be fixed by either GCC or LLVM, but until that happens (see
LLVM PR8152) lets use this workaround.
Prevent 'Line too long for provided buffer'.
We must skip using a buffer of length declared in cbc header, not 4096.
So perform the skip in bytecode.c rather than readdb.c (which doesn't know the
length). The skip in readdb.c is good for skipping the source code, so keep it.