-
Notifications
You must be signed in to change notification settings - Fork 37
Address Sanitizer integration #212
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
n1ywb-1
wants to merge
17
commits into
jrincayc:master
Choose a base branch
from
n1ywb-1:asan
base: master
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
Show all changes
17 commits
Select commit
Hold shift + click to select a range
fe1a4fd
Fix race between GC and case object construction
n1ywb-1 952f13c
Change slow GC to fast preallocation
n1ywb-1 5cc3e5b
Address sanitizer/GC integration
n1ywb-1 0965b9f
trying to fix gc bug
n1ywb-1 b121441
Restore SEG_SIZE 16000
n1ywb-1 0743b9e
FFFFFFFFFFFFFFFFFFFF
n1ywb-1 1e7df8e
Fix bufferoverrun in makehelp.c
n1ywb-1 744e7df
Use size_t for pointer arithmetic
n1ywb-1 79adac8
Use ASAN to poison free nodes
n1ywb-1 a02cdbe
Add address sanitizer instructions
n1ywb-1 ccf9893
Cleanup
n1ywb-1 d9f32de
fix pcons gdb macro
n1ywb-1 ec7a9b0
Fix strncpy warning
n1ywb-1 c7a84fa
Fix no-effect warn on poison node
n1ywb-1 8896137
Nuke pointless volatile qualifiers
n1ywb-1 c515508
Remove unused variable
n1ywb-1 5b51d32
Fix fake stack marking
n1ywb-1 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,71 @@ | ||
| This document describes how Address Sanitizer is integrated with ucblogo. | ||
|
|
||
| It has become best-practice to use such tools to verify C/C++ programs to help | ||
| ensure memory-safety, security, stability, rapid dev/text/debug cycles, etc. | ||
| That or don't use C. | ||
|
|
||
| Address Sanitizer (ASAN) is a runtime library developed by Google and integrated | ||
| into GCC (and clang) which can detect various types of subtle C memory | ||
| management bugs. | ||
|
|
||
| ASAN instruments code by rewriting it and managing variable allocation itself. | ||
| In order to check for stack related errors, it creates it's own "fake" stack on | ||
| the heap and allocates most (but not all) stack variables on the fake stack. | ||
|
|
||
| This is transparent to pure ANSI-C code that makes no platform-specific | ||
| assumptions. The stack is undefined behavior as far as C is concerned. | ||
|
|
||
| Unfortunately every practical mark and sweep memory manager for C makes platform | ||
| specific assumptions about the stack, as they must check it for accessible | ||
| memory objects. Fortunately this is a reasonable assumption for modern desktop | ||
| systems, which invariable feature a contiguously addressed stack on which | ||
| automatic variable are allocated, and, with some hacks, we can get the extents | ||
| and iterate it. | ||
|
|
||
| Unfortunately ASAN breaks this assumption by allocating stack frames on the heap | ||
| and putting pointers to them on the real stack, which adds a level of | ||
| indirection. | ||
|
|
||
| Of course Google would like to use ASAN to check Chrome, probably why they wrote | ||
| it, and Chrome uses a typical M&S GC with stack inspection. So they added an API | ||
| to ASAN to smooth over the differences with minor code changes. As the stack is | ||
| marked an ASAN function checks for pointers to fake stack frames and if found | ||
| returns the extents of the fake frame extents to also be marked. | ||
|
|
||
| ASAN also provides an API for manually poisoning memory regions, like free NODE | ||
| objects. | ||
|
|
||
| In our project most of this happens in mem.c, except for getting the address of | ||
| the bottom of the stack which is in main.c as always. | ||
|
|
||
| ASAN adds overhead resulting in about a 2x slowdown so it's not suitable for | ||
| production builds. Better performance can be obtained by enabling compiler | ||
| optimizations. | ||
|
|
||
| To build ucblogo with ASAN pass the flags in CFLAGS to the configure script, eg. | ||
|
|
||
| CFLAGS="-O2 -g3 -fsanitize=address -static-libasan -fno-omit-frame-pointer" CXXFLAGS="-O2 -g3 -fsanitize=address -static-libasan -fno-omit-frame-pointer" ./configure --prefix=$HOME --enable-objects | ||
|
|
||
| then make and test as normal. | ||
|
|
||
| To make GDB stop before exiting when ASAN hits a bug, set a breakpoint on the | ||
| ASAN Die function | ||
|
|
||
| break __sanitizer::Die | ||
|
|
||
| You may also find the following GDB breakpoints useful | ||
|
|
||
| break err_logo | ||
| dprintf mem.c:872,"free %V %V\n",nd,*nd | ||
| dprintf mem.c:299,"newnode %V %V\n",newnd,*newnd | ||
| break mem.c:299 | ||
| commands | ||
| bt | ||
| c | ||
| end | ||
|
|
||
| This will report where and when nodes are allocated and free-ed. It is especialy | ||
| useful in conjunction with -DSERIALIZE_OBJECTS so unique objects can be tracked | ||
| through their complete lifecycle. | ||
|
|
||
| More useful debugging tools are given in gdb.rc |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,52 @@ | ||
| # Dump a list of all nodes in all segments. | ||
| # Highly recommended to pipe output to a file | ||
| # pipe dumpnodes | cat > nodes.txt | ||
| define dumpnodes | ||
| set $seg=segment_list | ||
| while $seg | ||
| set $noden=0 | ||
| while $noden < $seg->size | ||
| set $node = $seg->nodes + $noden | ||
| printf "node %V %V %V %V\n",$node->id, $node->node_type, $node, *$node | ||
| set $noden=$noden+1 | ||
| end | ||
| set $seg=$seg->next | ||
| end | ||
| end | ||
|
|
||
| # Given an address, if it is a pointer to a fake stack variable, returns the | ||
| # pointer to the real stack frame. | ||
| # Otherwise returns NULL. | ||
| # Mostly useful for checking if a variable is on the ASAN fake stack or not. | ||
| define realstack | ||
| p (void*)__asan_addr_is_in_fake_stack( \ | ||
| (void*)__asan_get_current_fake_stack(), \ | ||
| $arg0, \ | ||
| NULL, NULL \ | ||
| ) | ||
| end | ||
|
|
||
| set $NT_LIST=010000 | ||
| set $NT_TREE=0100000 | ||
| set $NT_AGGR=020000 | ||
| set $NT_EMPTY=040000 | ||
| set $NT_CASEOBJ=000001 | ||
|
|
||
| # Walk and print a NODE tree. | ||
| define pcons | ||
| if $arg0 | ||
| printf "node %14.d %V %V %V\n",$arg0->id,$arg0->node_type, $arg0,*$arg0 | ||
| if $arg0->node_type != -1 && !($arg0->node_type & $NT_EMPTY) | ||
| if $arg0->node_type & $NT_TREE | ||
| pcons $arg0->nunion->ncons->nobj | ||
| end | ||
| if $arg0->node_type & $NT_LIST || $arg0->node_type & $NT_AGGR | ||
| pcons $arg0->nunion->ncons->ncar | ||
| pcons $arg0->nunion->ncons->ncdr | ||
| end | ||
| if $arg0->node_type & $NT_CASEOBJ | ||
| pcons $arg0->nunion->ncons->ncar | ||
| end | ||
| end | ||
| end | ||
| end | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hm, these might be redundant since this is now part of the NodeTypes enum.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I cut and pasted directly from the enum. They are redundant, but because these symbols are not defined in every scope GDB might break in, if the program is even still running (eg after a segfault), I came up with this.
There could be a better way, IDK. Probably not worth more effort unless you mean to use them.