boyski / audited-objects Goto Github PK
View Code? Open in Web Editor NEWA tool for build auditing and object recycling
A tool for build auditing and object recycling
openat, renameat, and unlinkat are all supported, but linkat is missing.
This is perhaps best described with an example.
Create a Makefile:
all: blah
sed -i s/hello/goodbye/ blah
blah:
echo "hello" > blah
Audit it, create a new makefile, and run it:
$ ao -osed.ao make
echo "hello" > blah
sed -i s/hello/goodbye/ blah
$ ao2make -MF Makefile.new -full -pdump sed.ao
+ make -r -q -p
$ make -f Makefile.new clean
Cleaning all targets ...
rm -f /home/user/test/blah
$ make -f Makefile.new
cd /home/user/test && sed -i s/hello/goodbye/ blah
sed: can't read blah: No such file or directory
make: *** [/home/user/test/blah] Error 2
Running AO on just the sed command gives the following:
$ ao -o- run sed -i s/hello/goodbye/ blah
31648,0,31647,myfci3.3syn34,6,u1204-2-6-0,,,sed,.,-,23639e99a31cc6eb8e71646733ead20488c13af6+28,8c421f4f207310e36c506d96bcd8b8176647a59d-1,sed -i s/hello/goodbye/ blah
X,init,0.0,31648,0,31647,0,-,23639e99a31cc6eb8e71646733ead20488c13af6+28,f,?,lkhdr3.0,64928,pnx,,,/bin/sed
C,rename,myfci3.3w74rc,31648,0,31647,0,-,23639e99a31cc6eb8e71646733ead20488c13af6+28,f,?,myfci3.3spqw3,8,pmc,dd7e1c6f0fefe118f0b63d9f10908c460aa317a6,,blah
U,rename,myfci3.3w6bfs,31648,0,31647,0,-,23639e99a31cc6eb8e71646733ead20488c13af6+28,u,?,0.0,0,0,,,sednNNqWp
The audit shows the blah
file being created through a rename (which is correct -- sed creates a temporary file then renames it), but there is nothing that says it needs the file to exist in the first place (i.e. there is nothing to show sed consumes the file in order to produce it).
I believe this is caused by the function ca_coalesce
in src/ca.c
. Perhaps the correct coalesce behavior is to only coalesce like access (coalesce all reads to a single read and all writes to a single write)?
This took awhile to track down...
When _FORTIFY_SOURCE
is defined and gcc optimizations are enabled, open*()
functions are redirected to __open*_2()
functions. AO needs wrappers for the __open*_2
fucntions.
Here is how I gleaned this information: http://git.overlays.gentoo.org/gitweb/?p=proj/sandbox.git;a=patch;h=15c12529fc53816d514d56a34e810ee010130c0b
Simple test (on Ubuntu 13.10):
$ echo "Helloworld" > somefile
$ ao -o- run tar -cf test.tar somefile
ENTERING creat_wrapper() => 0x00007fd5f0277840 [test.tar ...]
ENTERING open_wrapper() => 0x00007fd5f0276de0 [test.tar ...]
ENTERING fopen_wrapper() => 0x00007fd5f01ff2c0 [/etc/passwd ...]
Warning: no wrapper found for fclose()
ENTERING fopen_wrapper() => 0x00007fd5f01ff2c0 [/etc/group ...]
4859,0,4858,myowpd.98aj8g,19,u1204-2-6-0,,,tar,.,-,a84838f818148ce507f813c3afd9bb331f1aa1f0+25,5bdb7c78400f1c2391890ce8248b45cf420c81b2-2,tar -cf test.tar somefile
X,init,0.0,4859,0,4858,0,-,a84838f818148ce507f813c3afd9bb331f1aa1f0+25,f,?,m1q63k.0,307760,pnx,,,/bin/tar
R,fopen,0.0,4859,0,4858,0,-,a84838f818148ce507f813c3afd9bb331f1aa1f0+25,f,?,mwxq7z.tzsdt,921,plw,,,/etc/group
R,fopen,0.0,4859,0,4858,0,-,a84838f818148ce507f813c3afd9bb331f1aa1f0+25,f,?,mwxq7x.91a9r4,1802,plw,,,/etc/passwd
C,creat,myowpd.9boom0,4859,0,4858,0,-,a84838f818148ce507f813c3afd9bb331f1aa1f0+25,f,?,myowpd.9f4e61,10240,pmc,f40a0c91cff0ed541ca9950af3d59d6d08da72f1,,test.tar
somefile doesn't show up in the audit!
$ strace tar -cf test.tar somefile 2>&1 | grep somefile
execve("/bin/tar", ["tar", "-cf", "test.tar", "somefile"], [/* 20 vars */]) = 0
newfstatat(AT_FDCWD, "somefile", {st_mode=S_IFREG|0664, st_size=11, ...}, AT_SYMLINK_NOFOLLOW) = 0
openat(AT_FDCWD, "somefile", O_RDONLY|O_NOCTTY|O_NONBLOCK|O_NOFOLLOW|O_CLOEXEC) = 4
write(3, "somefile\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0"..., 10240) = 10240
Openat is being called, but AO can't see it. The reason is what I described above. Strace uses ptrace so it still sees the call to openat (after the call to __openat_2).
This is solvable by adding wrappers for all the __open*_2
functions that call the existing openat_wrapper
.
libAO.so contains the symbol hash_init, which is also contained in libgettextlib-0.18.3.so. This causes the tool msgfmt (from the gettext package) to segfault.
$ objdump -x .Linux_x86_64/libAO.so | grep hash_init
00023a81 l F .text 0000008e hash_init
0003c598 g F .text 00000020 git_hash_init
$ objdump -x ./gettext-tools/gnulib-lib/.libs/libgettextlib-0.18.3.so | grep hash_init
000000000002da40 g F .text 0000000000000050 hash_init
This can be reproduced quite easily:
$ cat hash.c
#include <stdio.h>
void hash_init () {
printf("Hello hash_init\n");
}
$ cat test.c
int main() {
hash_init();
}
$ gcc -fPIC -c hash.c
$ gcc -shared -o libhash.so hash.o
$ gcc test.c -L. -lhash -Wl,-rpath .
$ ./a.out # works just fine
Hello hash_init
$ ao run ./a.out # segfaults
ao: Error: ./a.out: Segmentation fault (coredump)
ao: Warning: 1 audits left over:
Here's an example:
$ ao run ./gradlew assemble
Assertion failed: (path), function pn_new, file ./pn.c, line 94.
Starting a Gradle Daemon (subsequent builds will be faster)
Assertion failed: (path), function pn_new, file ./pn.c, line 94.
Could not write standard input into: Gradle build daemon.
java.io.IOException: Stream closed
at java.lang.ProcessBuilder$NullOutputStream.write(ProcessBuilder.java:433)
at java.io.OutputStream.write(OutputStream.java:116)
at java.io.BufferedOutputStream.flushBuffer(BufferedOutputStream.java:82)
at java.io.BufferedOutputStream.flush(BufferedOutputStream.java:140)
at org.gradle.process.internal.streams.ExecOutputHandleRunner.run(ExecOutputHandleRunner.java:56)
at org.gradle.internal.concurrent.ExecutorPolicy$CatchAndRecordFailures.onExecute(ExecutorPolicy.java:54)
at org.gradle.internal.concurrent.StoppableExecutorImpl$1.run(StoppableExecutorImpl.java:40)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
FAILURE: Build failed with an exception.
* What went wrong:
Unable to start the daemon process.
This problem might be caused by incorrect configuration of the daemon.
For example, an unrecognized jvm option is used.
Please refer to the user guide chapter on the daemon at https://docs.gradle.org/3.1/userguide/gradle_daemon.html
Please read the following process output to find out more:
-----------------------
* Try:
Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output.
> Starting Daemonao: Warning: audit group closed with 2 pending audits
ao: Warning: /private/var/folders/fb/3v_41kkj05lchxcrm1vwvd0c0000gn/T/hsperfdata_emanuelez/4800: No such file or directory
ao: UPLOADING /Users/emanuelez/.gradle/daemon/3.1/registry.bin
ao: UPLOADING /Users/emanuelez/.gradle/daemon/3.1/registry.bin.lock
ao: UPLOADING /Users/emanuelez/.gradle/native/21/osx-amd64/libnative-platform-curses.dylib.lock
ao: UPLOADING /Users/emanuelez/.gradle/native/21/osx-amd64/libnative-platform.dylib.lock
ao: ARCHIVING /Users/emanuelez/.gradle/daemon/3.1/registry.bin.lock
$ make
cd src && make -s rt TGTARCH=
OS_CPU=Linux_x86_64
aotool.c: In function ‘_name_pathstate’:
aotool.c:160:19: error: storage size of ‘stbuf’ isn’t known
aotool.c:166:5: error: implicit declaration of function ‘stat64’ [-Werror=implicit-function-declaration]
aotool.c:160:19: error: unused variable ‘stbuf’ [-Werror=unused-variable]
aotool.c: In function ‘do_action’:
aotool.c:365:22: error: storage size of ‘stbuf’ isn’t known
aotool.c:375:3: error: implicit declaration of function ‘lstat64’ [-Werror=implicit-function-declaration]
aotool.c:365:22: error: unused variable ‘stbuf’ [-Werror=unused-variable]
cc1: all warnings being treated as errors
make[1]: *** [aotool.o] Error 1
make: *** [java/WebContent/client/ao--3.8.0-29-generic.tar.gz] Error 2
I was able to run the ao client properly on Linux.
It does not seem to work on OSX:
ao -o - run uname
Darwin
I used the version available on sourceforge.
I tried building from source from this repository with the same result.
On ubuntu 12.04 LTS server 64 bits using a fresh checkout, I am getting this error:
~/tools/audited-objects$ make
cd src && make -s rt TGTARCH=
OS_CPU=Linux_x86_64
aotool.c: In function ‘_name_pathstate’:
aotool.c:160:21: error: storage size of ‘stbuf’ isn’t known
aotool.c:166:5: error: implicit declaration of function ‘stat64’ [-Werror=implicit-function-declaration]
aotool.c:160:21: error: unused variable ‘stbuf’ [-Werror=unused-variable]
aotool.c: In function ‘do_action’:
aotool.c:365:22: error: storage size of ‘stbuf’ isn’t known
aotool.c:375:3: error: implicit declaration of function ‘lstat64’ [-Werror=implicit-function-declaration]
aotool.c:365:22: error: unused variable ‘stbuf’ [-Werror=unused-variable]
cc1: all warnings being treated as errors
make[1]: *** [aotool.o] Error 1
make: *** [java/WebContent/client/ao--3.8.0-29-generic.tar.gz] Error 2
When auditing a sudo
process (ao -o- run sudo touch blah
)** the following message is printed:
sudo: Warning: LD_PRELOAD setting lost in exev[lv]e() call
The process that is called by sudo is also not audited.
The code that prints the warning is in libunix.c line 437 and gives this comment:
If the host process assembles a custom environment which
does not retain LD_PRELOAD, that process branch will be
unaudited. This is a hole we ought to plug but it seems
unlikely so for now we will just warn about it. If it
ever actually happens it should be easy enough to fix.
So it looks like sudo
is axing LD_PRELOAD
(the man page confirms this) and the variable needs to be re-injected.
** In order to audit a setuid process in linux you need to copy the 64-bit libAO.so to /lib/x86_64-linux-gnu/libAO.so and the 32-bit libAO.so to /lib/libAO.so. They also need to owned by root:root
and have the setuid bits set (-rwsr-sr-x
).
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.